포인터
1. 포인터
포인터는 메모리 주소에 접근한다.
먼저 메모리 주소를 반환하기 위해서는 & 키워드를 사용한다.
int num = 10;
printf("%d", num); // 10
printf("%p", &num); // 0x7ffe5367e044
포인트 변수의 선언은 * 키워드를 사용하고 자료형 뒤에 붙을 수도 있고 변수명 앞에 붙을 수도 있다.
int num = 10;
int *ptr = # // 0x7ffe5367e044 주소값 대입, 변수명에 * 붙임
int* ptr2 = # // 0x7ffe5367e044 주소값 대입, 자료형에 * 붙임
포인터 변수는 대입한 주소값을 출력한다.
printf("%p", ptr); // num의 주소값, 0x7ffe5367e044 출력
ptr 포인터는 아래와 같은 구조를 가진다.
| 변수명 | 메모리 주소 | 값 |
|---|---|---|
| num | 0x7ffe5367e044 | 10 |
| ptr | 0x7ffe70f9d8f8 | 0x7ffe5367e044 |
포인터를 이용해서 num의 값을 출력하고 싶다면 * 키워드를 사용한다.
printf("%d", *ptr); // 10
다음은 포인터의 값을 넣는 연산의 예이다.
int num = 10;
int *ptr = #
printf("%d\n", num); // 10
*ptr += *ptr +1; // num = num + (num + 1) 과 같음.
printf("%d\n", *ptr); // 21
2. 포인터와 배열
배열은 각 요소마다 독립적인 메모리를 소유하며 변수명은 배열의 첫번째 주소값을 가지는 포인터이다.
int[] nums = {10, 20, 30, 40};
printf("%p", nums); // 0x5ffe70f9d8f8
printf("%p", &nums[0]); // 0x5ffe70f9d8f8
printf("%p", nums[0]); // 10
포인터와 순번을 결합하여 배열의 데이터를 읽고 쓸수 있다.
int arr[] = {1,2,3};
printf("%d\n",arr[0]); // 0번째 값 출력
printf("%d\n", arr[1]); // 1번째 값 출력
printf("%d\n", arr[2]); // 2번째 값 출력
printf("%d\n", *arr); // 0번째 값 출력
printf("%d\n", *(arr + 1)); // 1번째 값 출력
printf("%d\n", *(arr + 2)); // 2번째 값 출력
*(arr + 2) = 4; // 2번째 값으로 4 할당
printf("%d\n", *(arr + 2)); // 4가 출력
포인터도 배열이 있다.
먼저 일반 배열은 다음과 같이 표현한다.
char Array[3][10] = {"what", "are", "you"};
// 3행 10열의 배열이 생성
| 0 | 1 | 2 | 3 | 4 | 5 | 6 | 7 | 8 | 9 | |
|---|---|---|---|---|---|---|---|---|---|---|
| 0 | w | h | a | t | ||||||
| 1 | a | r | e | |||||||
| 2 | y | o | u |
위 배열에서는 값이 없는 빈 배열 공간이 많이 생긴다.
하지만 포인터는 필요한 만큼의 배열을 가질 수 있다.
char *myArray[3] = {"what", "are", "you"};
// 3행이 생기고 각 글자 크기만큼 열이 생김
| 0 | w | h | a | t | ||||||
| 1 | a | r | e | |||||||
| 2 | y | o | u |
다음은 문자열과 포인터의 접근 방식을 다음과 같다.
char *p = "KOREA";
printf("%s\n", p); // 0번째 부터 읽음, KOREA
printf("%s\n", p+3); // 3번째 부터 읽음, EA
printf("%c\n", *p); // 0번째, K
printf("%c\n", *(p + 3)); // 3번째, E
printf("%c\n", *p + 3)); // 0번째 문자 K 유니코드값(112)과 + 3을 더한 값 (115)=> M
3. 포인터와 함수
함수 포인터를 이용하면 하나의 함수 포인터로 여러 함수 기능을 스위칭할 수 있다.
이때는 변수의 주소값 반환처럼 &기호를 붙일 필요가 없다.
void sum(int a, int b) {
printf("%d", a + b);
};
void avg(int a, int b) {
printf("%d", (a + b) / 2);
};
void (*func)(int a, int b);
void main(){
int a =10, b=5;
func = sum;
func(a, b);
// 15
func = avg;
func(a, b);
// 7
}
끝.
Leave a comment