Pointer(포인터)
메모리 "주소"를 저장하는 "변수"
"아니 그게 뭔말이에요...? 그건 뭐 언제 왜 쓰는데요;;;;"
만약에, a라는 변수가 있다고 해봅시다.
int a = 10;
해당 변수는 메모리 영역 어딘가에 "주소"를 가지고 자리 잡고 있을겁니다.
그리고 그 주소안에는 10이라는 정수가 살고있죠. 만약에 a가 가지고 있는 값을 다른 주소에 저장하고 싶다면?
int a = 10;
int b = a;
위 코드와 같이 int b = a 와 같다고 선언함으로써 b는 a값을 가지게 됩니다!
근데 뭔가 궁금한게 생기지 않나요?
저렇게 b = a 라고 선언하면 b가 a의 주소를 가지고 주소안에 있는 값을 가지는 걸까?
아니면 a값을 복사해서 b의 주소안에 넣는 걸까?
위와 같이 선언하게 되면 b는 a의 주소안에 있는 10이라는 값을 복사해서 b의 주소에 저장하게 됩니다.
즉, 값이 똑같은데 메모리 영역은 2개를 차지하게 되는거죠 !!! 이렇게 되면 불필요한 메모리를 사용하게 되는겁니다.
Pointer
자 그러면 포인터는 "주소"를 "변수"에 저장한다고 했습니다.
그렇게 되면 메모리는 하나뿐인데 a, b는 같은 값을 가지게 되겠죠? 코드로 한번 해봅시다.
int a = 10;
int* b = &a;
*, &라는 연산자를 활용한걸 확인 할 수 있습니다.
* 연산자 : 포인터 변수가 가리키는 메모리 주소에 저장된 값을 가져옵니다. int* b 는 포인터 변수라고 선언하는것 입니다.
& 연산자 : 변수의 메모리 주소를 구할 때 사용됩니다.
// 변수 a선언
int a = 10;
// b는 포인터를 의미한다. 초기화 값은 a변수의 메모리 주소다.
int* b = &a;
std::cout << *b << std::endl; // 10
&a를 사용하여 a변수의 메모리 주소값을 가져옵니다. 그리고 *b 포인터 변수에 메모리 주소값을 저장합니다.
*b를 통해 메모리 주소에 저장된 값을 가져옵니다 -> 10
b에 들어가 있는 값을 초기화 하면 a도 변할까?
b에는 a변수의 메모리 주소값이 들어가있습니다. 그안에 값에 접근을 하여 다른 값으로 초기화 한다면 a값도 변하지 않을까요???
int a = 10;
int* b = &a;
*b = 40;
std::cout << a << std::endl; // 40
예상했던것 처럼 똑같은 메모리를 사용하기에 포인터 b에서 값에 접근하여 초기화시 a의 값도 변하는걸 확인할 수 있습니다 :)
심화 - 메모리 영역내에서 포인터의 위치
자 포인터가 메모리 영역에 대해 나타내는걸 알았으니, 메모리 영역의 구조에 대해 간단하게 나마 알아봐야겠죠?
다음과 같이 변수를 선언했다고 해봅시다.
int a = 10;
int b = 20;
int* c = &a;
std::cout << *c << std::endl; // 10
포인터 c의 메모리 주소는 a변수 메모리 주소를 가지고 있습니다. 그래서 출력 시 10이라는 값이 나오죠!
int* c = &a+1;
std::cout << *c << std::endl; //1861923792
a변수 다음으로 b를 선언했기에 a주소값 다음은 b가 나올거라 예상을 보통 합니다.
하지만 포인터에 +1 만큼 주소를 이동시키고 출력을 해보면 예상치 못한 값이 나오게 됩니다.
즉, 메모리는 순서대로 딱딱 옆에 붙어서 할당되는게 아니라 랜덤으로 어딘가에 위치하게 됩니다 :)
그렇다면, 메모리가 옆으로 나열되는 경우는 언제일까요???
배열의 메모리 영역
int arr[] = {1,6,4,5,2};
int* ptr = arr;
std::cout << *ptr << std::endl; // 1
std::cout << *(ptr+1) << std::endl; // 6
*ptr은 arr의 메모리 주소값을 가지고 있습니다. 그래서 ptr을 출력 해보면 첫번째 메모리 값인 1이 출력됩니다.
여기서 포인터의 위치를 +1 이동시키면 다음 메모리 주소의 값인 6이 출력됩니다.
이와 같이 배열과 같은 구조에서는 메모리영역이 순서대로 나열되 있는 형태를 띄우게 됩니다 :)
오늘도 슬기로운 코딩 생활 하시길 바라며,
궁금하신 점이나 잘못 기재된 점에 대한 피드백은 언제나 환영입니다 !