포인터(pointer)란 메모리 주소를 저장하는 변수입니다. 일반 변수는 데이터 자체를 저장하지만, 포인터는 데이터를 저장하는 메모리의 "위치"를 저장하는 것입니다.
int number = 10; // 일반 변수 선언 및 초기화
int* ptr = &number; // number의 주소를 ptr에 저장
위 코드에서 ptr은 number의 메모리 주소를 가리킵니다. 즉, ptr을 이용하면 number가 저장된 메모리 공간에 접근할 수 있습니다.
포인터는 일종의 "포탈"처럼 작동하여 특정 메모리 위치로 이동하여 값을 읽거나 수정할 수 있습니다.
이를 그림으로 표현하면 다음과 같습니다.
| 메모리 주소 | 값 | 변수명 |
|---|---|---|
| 0x1000 | 10 | number |
| 0x2000 | 0x1000 | ptr |
number는 메모리 0x1000에 저장된 변수이며, 값은 10입니다.ptr은 0x1000이라는 주소를 가리킵니다. 즉, ptr을 통해 number 변수의 값에 접근할 수 있습니다.포인터를 활용하면 변수를 직접 수정하지 않고도 값을 변경할 수 있습니다.
#include <iostream>
using namespace std;
void SetHp(int* hp)
{
*hp = 100; // 포인터가 가리키는 주소의 값을 100으로 변경
}
int main()
{
int hp = 1; // 'hp'라는 정수형 변수 선언 및 초기화
SetHp(&hp); // 'hp'의 주소를 전달하여 함수 내에서 값을 수정
cout << "현재 HP: " << hp << endl; // 출력: 현재 HP: 100
return 0;
}
SetHp(int* hp) 함수는 매개변수로 포인터를 전달받아 *hp = 100;을 실행하여 해당 주소의 값을 100으로 변경합니다.main()에서 hp 변수의 주소 &hp를 SetHp() 함수에 전달하면 hp 값이 함수 내에서 직접 변경됩니다.int number = 1;
int* ptr = &number; // number의 주소를 ptr에 저장
ptr은 number의 주소를 가리키며, 이를 통해 number 값을 읽거나 수정할 수 있습니다.int value1 = *ptr; // ptr이 가리키는 주소의 값을 가져와 value1에 저장
*ptr을 사용하면 ptr이 가리키는 변수의 값을 읽을 수 있습니다.*ptr = 2; // ptr이 가리키는 주소의 값을 2로 변경 (즉, number의 값이 2로 변경됨)
ptr을 통해 number 값이 1 → 2로 변경됩니다.포인터의 크기는 운영체제와 컴파일러 아키텍처에 따라 달라집니다.
4바이트8바이트즉, 포인터 자체는 데이터 타입과 무관하게 고정된 크기를 가집니다.
int* ptr;
double* dptr;
char* cptr;
int*, double*, char*)은 해당 포인터가 가리키는 데이터의 타입을 의미합니다.ptr + 1)이 수행될 때 몇 바이트씩 이동해야 하는지 결정됩니다.int number = 1;
__int64* ptr2 = (__int64*)&number; // number 주소를 강제로 8바이트 포인터로 변환
*ptr2 = 0xAABBCCDDEEFF;
number는 4바이트(int)이지만, 8바이트(__int64*) 포인터를 사용하여 값이 덮어씌워집니다.어셈블리 코드를 통해 포인터의 동작을 확인할 수 있습니다.
#include <iostream>
using namespace std;
int main()
{
int number = 1;
int* ptr = &number;
int value1 = *ptr;
*ptr = 2;
return 0;
}
lea eax, [number] ; number의 주소를 eax 레지스터에 저장
mov dword ptr [ptr], eax ; eax 값을 ptr에 저장
mov eax, dword ptr [ptr] ; ptr이 가리키는 값을 eax에 저장
mov dword ptr [value1], eax ; eax 값을 value1에 저장
mov eax, dword ptr [ptr] ; ptr이 가리키는 값을 eax에 저장
mov dword ptr [eax], 2 ; eax가 가리키는 주소의 값을 2로 변경
잘못된 메모리 접근 (Segmentation Fault)
int* ptr;
*ptr = 100; // 오류 발생 (ptr이 유효한 주소를 가리키지 않음)
Dangling Pointer (삭제된 메모리 접근)
int* ptr = new int(10);
delete ptr;
*ptr = 20; // 오류 발생 (할당 해제된 메모리에 접근)
메모리 누수 (Memory Leak)
new로 동적 할당한 메모리를 delete로 해제하지 않으면 메모리 누수가 발생합니다.int* ptr = new int(10);
// delete ptr; // 해제를 잊으면 누수가 발생