[자료구조] C언어에서 포인터
in Study on Data Structure
컴퓨터에서 포인터란?
자료가 저장된 위치를 가리키는 데이터를 일컫는다.
C언어에서 포인터를 선언할 수 있고, 파이썬에서도 링크드리스트 자료구조를 만드는 과정에서 포인터를 활용한다.
C언어에서의 포인터
C언어에서는 할당된 메모리의 위치를 가리키는 포인터 변수를 선언할 수 있다.
#include <stdio.h>
int main() {
// int *numPtr = &num1; 이렇게도 선언 가능.
int num1 = 10;
int *numPtr = &num1; // 포인터 변수 선언, num1이 저장된 주소를 저장
printf("%i\n", num1); // num1 값을 출력
printf("%p\n", &num1); // num1이 저장된 주소를 출력
printf("%p\n", numPtr); // numPtr 자체가 주소이므로 주소를 출력
printf("%i\n", *numPtr); // numPtr 주소 안에 저장된 값을 출력
return 0;
}
여기서 num1은 num1이라는 변수에 값을 저장하는 것이고,
numPtr은 값을 저장하는 메모리의 위치, 주소를 가리키는 역할을 한다.
아파트에 비유를 해보자.
아파트 건물 한 채가 있다.
이 아파트에는 총 20세대가 있으며, 각 층마다 2세대가 거주하고 있다.
즉, 101호, 102호, 201호, 202호, … , 1001호, 1002호가 있는 구조이다.
이때, 102호에 “누리”라는 사람이 살고 있다.
아파트 건물을 메모리칩, 아파트 각 세대를 메모리, 101호, 102호 등 집 주소를 메모리 주소로, 그 집에 사는 사람을 변수에 비유할 수 있다.
즉 102호라는 메모리는 “누리”라는 사람이 거주하도록 할당된 것이다.
이를 따라 위에 누리네 집을 코드에 비유하면 아래와 같다.
주소 : 102호
거주자 : "누리"
*102호 = "누리" // 102호에는 누가 살고 있는가? = 누리
102호 = &"누리" // 누리는 어디에 살고 있는가? = 102호
즉, (자료형 * pointer) 형태를 통해서 값을 저장할 주소를 변수로 선언할 수 있으며, printf를 통해
int a = 23;
int * pointer = &a;
printf("%p\n", pointer);
printf("%i\n", *pointer);
결과
23이 저장된 메모리의 주소
pointer라는 메모리 주소에 저장된 정수 값 (= 23)
이렇게 활용할 수 있다.
주의사항
데이터 타입의 일치
int a = 3;
double b = 3.321;
int* p1 = &a;
double* p2 = &b;
위와 같이 포인터를 선언할 때 변수 타입은 무조건 일치하도록 선언해야 한다.
데이터 타입마다 할당되는 크기가 다르기 때문이다.
- int : 4바이트
- double : 8바이트
- char : 1바이트
포인터 변수를 선언할 때
int* p;
int *p;
위 두 형태 중 어느 것을 선언하여도 결과는 같다.
이렇게 *이 붙는 순간 p는 주소를 저장하는 포인터 변수가 되는 것이다.
기타
파이썬에서도 링크드리스트나 트리를 만드는 과정에서 객체와 객체를 연결할 때 포인터가 그 역할을 하며 자료구조를 형성하는 것을 알 수 있었다.