본문 바로가기

C언어

Chapter 13. (int *)pointer

Chapter 13.(int*)pointer

int pointer= 5;

(int *)pointer

(int *)pointer를 이용해서 나온 값과 그냥pointer를 이용해서 출력되는 값은 어떤 차이점이 있을까?

캐스트 연산자의 이해

13_1.c

#include <stdio.h>

main()
{
int pointer = 5;

printf("(int *)pointer = %#010x\n", (int *)pointer);
}

gcc -o 13_1 13_1.c

./13_1

(int *)pointer = 0x00000005

위의예제를통해 결과를확인하기 전에"5가 메모리 어딘가에 저장디어 있고이곳의 번지를 리턴할 것이다"라고 예상한다.

하지만, pointer변수에 들어 있는 정수 값이 출력된다.

위의 질문에 대한 결론을 말하자면 pointer를 이용하여 출력된 값은 정수 값이고 (int *)pointer를 이용해서 나오는 값은 번지 값이다.

int pointer = 5;

(int)pointer; (1)

(float)pointer; (2)

(int *)pointer; (3)

(1),(2)는 int형으로 정의된 pointer라는 변수를 각각 int, float형으로 변환하는 식이다. 수식의 값은 각각 5와 5.0이 될 것이다.

그와 마찬가지로(3)은pointer에 들어있는 값을 정수형이 아닌 정수형 포인터로 만든다.즉,pointer값 자체가 주소화 되는 것이다.

13_2.c

#include <stdio.h>

main()
{
int imsi, *imsip;
int temp;

imsi = 5;

imsip = &imsi;

printf("imsip[%#010x] :: &imsi[%#010x]\n", imsip, &imsi); (1)

temp = imsip;
printf("temp[%#010x] :: imsip[%#010x]\n", temp, imsip);(2)

printf("*temp[%d], *imsip[%d]\n", *temp, *imsip); (3)

printf("*((int *)temp)[%d], *imsip[%d]\n", *((int *)temp), *imsip); (4)
}

gcc -o 13_213_2.c

./13_2

imsip[0xbfad35b8] :: &imsi[0xbfad35b8]
temp[0xbfad35b8] :: imsip[0xbfad35b8]
*((int *)temp)[5], *imsip[5]

imsi라는 정수형 변수가 메모리의 어딘가에 저장되어 있을 것이고 그 주소가 imsip에 저장된다.

따라서, imsip는 imsi를 가리키는 형태가 된고 (1)의 식을 통해 같은 주소 값이 출력된다.

temp는 정수형 변수이므로 "이 변수에는 정수형값을넣을 수 있다"가 된다.

하지만,imsip에 저장되어 있는 주소 값을 강제적으로temp에 넣고 있어 캐스트 연산자를사용하지 않아 컴파일시에아래와 같은 경고문이 출력된다.

13_2.c:12: warning: assignment makes integer from pointer without a cast

(2)의 식을 통해 같은 결과값이 출력됨을 알 수 있다. 하지만,temp에 들어 있는값은 정수이고 imsip에 들어 있는 값은 주소 값이다.

(3)의 식에서 *imsip는 imsip에 들어 있는 주소 값으로 이동하여 그곳에 저장된 값을 꺼내오라는건데, *temp도 같은 의미일까?

당연히,그렇게 되면 안된다. temp에 들어있는값은 이미 말한것처럼 정수값이므로 '*' 연산자를 사용할 수 없다.

(3)의 식에 대해서 컴파일 해보면 아래와같은 에러가 발생할 것이다.

13_2.c:14: error: invalid type argument of 'unary *'

이제 (4)의 식을살펴보자. 이부분이 중요한 부분이다.

temp에는 imsip에 들어 있던 주소값이 저장되어 있다고 이미 말했다.

그러므로(int *)temp는 곧 "temp에 저장된 정수 값을 주소로 변환한 후 그 주소 값을 리턴한다"라는 의미가 된다.

당연히 아래와 같이 (int *)temp를 출력해보면imsip에 들어있던 주소 값과 동일한 값이 출력될 것이다.

따라서, '*'연사자를 사용,*((int *)temp), temp에 들어 있는 주소를 참조하여 그 참조된 곳에서 값을 꺼내올 수 있게 된다.

(int *)pointer는pointer에 들어 있는 값을 주소를 의미하는 값으로 바꾸고 *((int *)pointer)는 그 주소 값을 참조하여 값을 하나 취한다.

'C언어' 카테고리의 다른 글

Chapter 16. 함수 포인터  (0) 2011.10.16
Chapter 17. 구조체와 포인터  (0) 2011.10.16
Chapter 14. void형 포인터  (0) 2011.10.16
Chapter 10. 바로알자 getchar()  (0) 2011.10.16
Chapter 11. 가변 인자  (0) 2011.10.16