프로그래밍/C 2013. 4. 19. 00:09

포인터는 변수이다. 포인터는 메모리 번지를 저장하는 변수이다. 다음 정의에서

 

  int   i;

  int* pi;

 

는 모두 변수이다. 차이점이 있다면 i는 값을 저장하기 위한 변수이고, pi는 메모리 번지를 저장하기 위한 변수이다.

 

i 및 pi가 차지하는 메모리 공간은 4바이트이다. 그렇다면 두 변수는 서로 성질은 틀리지만 값을 교환할 수 있다.

다음은 i 및 pi의 사용이다.

 

  int   i;

  int* pi;

  i = 50;

  pi = &i;          // 변수 pi에 i의 번지값을 대입

  pi = (int*)i;    // 변수 pi에 i의 값을 대입

 

위 코드에서 pi는 i의 번지가 아닌 i의 값을 갖게 된다.

 

  int   i;

  int* pi;

  i = 50; 

  pi = (int*)i;    // 변수 pi에 i의 값을 대입, pi는 i의 값 50을 메모리 번지로 대입 받는다.

  printf( "%d ", pi );   // 50이 출력, 변수 pi의 값을 출력하기 때문에

  *pi = 30;      // pi는 i의 값 50을 갖고 있으므로, *pi는 50번지를 접근하게 된다.

                            // 메모리 번지 50번지는 일반적으로 접근할 수 없는 번지이니까 프로그램 다운된다.

                            // 만약 i가 50이 아니라 특정 변수의 주소값이었다면, 그 특정 변수에 접근은 가능할

                            // 것이다.

 

결국 존재하지 않는 임의의 번지를 위와 같이 pi에 넣을 수는 있지만, 옳지 않은 번지를 접근함으로써 프로그램은

다운된다. 그렇기 때문에 C 언어는 이를 다음과 같이 직접 대입할 경우 경고 에러(Warning Error)를 발생시킨다.

 

   pi = i;      // warning C4047: '=' : 'int *' differs in levels of indirection from 'int '

 

정리하면, 포인터 변수와 일반 데이터 변수간에는 그 값을 맞교환할 수 있지만, 그 사용에 있어서는 주의를 해야 한다.

다음 코드는 어떨까? 내가 나의 번지를 갖고 있다가 나한테 접근해서 값을 바꾼다.

 

  int  i = 5;

  i = (int)&i;      // i에 i의 번지를 대입
  printf( "i의 주소는 %#X \n", i );   // i의 주소는 0X12FF7C

  *(int*)i = 100;
  printf( "i의 값은 %d \n", i );
          
// i의 값은 100

 

다음 코드는 함수 포인터를 대신해서 사용되는 i 변수이다. 변수 i는 4바이트 크기를 갖기 때문에 함수 포인터로 동작할

수 있다.

 

  #include <stdio.h>

  int count = 0;

  void main( void 
  {
      int  i;

      i  =  (int)main;

      printf( "%d ", count++ );

      ( (void(*)(void)) i ) ();   // main() 함수를 직접 호출하는 것과 동일

                                                          // i를 함수 포인터로 먼저 캐스팅한 후 함수화
  

}


출처 : http://blog.naver.com/PostList.nhn?blogId=eunchol71

'프로그래밍 > C' 카테고리의 다른 글

Vi 편집기 setting  (0) 2013.04.19
linux kernel에서 쓰이는 자료구조.(double linked list and tree)  (0) 2013.04.19
Double linked list with using array  (0) 2013.04.19
함수 포인터  (0) 2013.04.19
linked list [펌]  (0) 2013.04.19
//