void 형 포인터와 널 포인터 | c Note 2004/09/06 21:49
http://blog.naver.com/bravedog/100005562577

void 포인터란 데이터 형이 정해지지 않은 포인터를 말한다. 프로그램을 만드는 경우 필요에 따라서  여러 타입의 데이터형을 일괄적으로 처리할 일이 발생한다. 하지만 각각의 데이터 형마다 포인터를 만든다면 메모리의 낭비도 발생할 뿐만 아니라 소스가 엄청나게 길어진다. 이러한 문제를 해결하기 위한 포인터가 바로 void 포인터이다. void 포인터는 개게가 존재하는 위치와 타입만 알면 하나의 포인터로 여러 데이터 형을 처리할 수 있다.

 

void 포인터는 타입캐스팅이 없이는 참조할 수가 없다. 그 이유는 포인터가 가리키는 객체의 크기를 컴파일러가 결정할 수 없기 때문이다. 또한 void 포인터는 포인터 연산을 할수가 없다. 일반적으로 void 포인터는 메모리에 직접 접근할 대 사용한다.

 

다음 예제를 보고 void 포인터의 사용법을 알아보자.

 1  #include <stdio.h>
 2
 3  int main()
 4  {
 5      int x = 3;
 6      float f = 0.0f;
 7      void *p;            // void 형 포인터 선언
 8
 9      // 기존 값 출력
10      printf("x = %d, f = %f\n",x,f);
11
12      p = &x;             // x를 가리킨다
13      *(int*)p = 2;
14      p = &f;             // f를 가리킨다
15      *(float*)p=1.5f;
16
17      // 변경 값 출력
18      printf("x = %d, f = %f\n",x,f);
19
20      return 0;
21  }

 

결과화면

 

 

 

 

 

 

 

 

 

위의 예제에서 void 형 포인터 변수 p를 이용하여 각각의 변수에 값을 대입할 경우 타입캐스팅이 일어났음을 확인할 수 있다. 주의할 점은 void 형 포인터 변수 p도 포인터이기 때문에 타입캐스팅을 할 경우 데이터 형 뒤에 반드시 '*'을 붙이기 바란다.

 

 

한편, 포인터 중에는 아무 것도 가리키지 않는 NULL 포인터라는 것이 있다. NULL 포인터는 포인터의 초기화나 비교, 리턴값으로 많이 사용한다. 그럼 NULL포인터의 쓰임새를 잠시 살펴보자.

 

첫 번째로 NULL 포인터는 포인터의  초기화를 위해서 많이 사용된다. 예를 들어 나중에 사용할 포인터이지만 현재는 아무 것도 가리키지 않고 있다는 의미를 주기 위해서 NULL포인터로 초기화한다

 

int *pLater = NULL;

 

두 번재로 NULL 포인터는 현재 포인터가 가리키는 곳이 있는지 없는지를 확인하기 위해서 비교의 용도로 많이 사용된다. 따라서 어딘가 가리키는 곳이 있다면 그 포인터는 NULL이 될 수가 없겠지!?

 

if(pLater == NULL){

    // 가리키는 곳이 없으므로 포인터 사용불가

}

else {

    // 가리키는 곳이 있으므로 포인터 사용가능

}

 

이러한 비교식에서 C언어는 편리성을 위해 다음과 같이 간단한 표현식을 사용할 수 있다.

if(!pLater){}

위의 표현은 부정 연산자(!)를 사용한 것인데 '포인터 형 변수 pLater가 가리키는 곳이 없으면'라는 의미를 가진다. 'NULL 포인터와 같다'는 의미와 상통한다.

 

세 번째로 NULL 포인터는 메모리가 할당되지 않았음을 의미한다. 예를 들어 동적 메모리를 생성하는 malloc함수는 메모리 생성에 실패하면 NULL포인터를 리턴한다. 만약 NULL포인터를 리턴한다면 메모리가 생성되지 않았으므로 사용하면 안되겠지?

 

// 메모리 할당

pLater = (int*)malloc(10*sizeof(int));

if(pLater == NULL){

    // 메모리가 생성되지 않았으므로 처리

}

 

이렇게 NULL 포인터가 사용되는 용도는 크게 세 가지 정도로 정리할 수 있다.

 

그럼 좀 더 나아가 NULL포인터의 내부로 들어가 보자.

 

#define NULL 0

 

NULL 포인터가 0으로 정의되어 있지만 반드시 0이지는 않다. 환경에 따라서 NULL 포인터는 다른 값을 수도 있다. 그렇지만 공통적으로  NULL이란 매크로를 사용한다는 것을 기억해 두기 바란다. 개인적으로는 NULL이란 매크로를 사용할 것을 추천한다.

 

 

tip

포인터를 이용하여 프로그램을 하다보면 실행중에 다음과 같은 문장을 종종 발견할 수 있다.

null pointer assignment

이 메시지는 초기화하지 않은 포인터를 사용하여 잘못된 위치에 데이터를 쓰려고 할 때 발생한다. 이러한 경우는 초기화하지 않고 사용하는 포인터가 있는지 확인해 보기 바란다.

'c or linux' 카테고리의 다른 글

원형(prototype) 강화하기  (0) 2005.03.09
배열 포인터  (0) 2005.03.09
void 형 포인터와 널 포인터  (0) 2005.03.09
포인터의 포인터  (0) 2005.03.09
동적 메모리 - 메모리 할당  (0) 2005.03.09
동적 메모리 - 메모리 크기 변경  (0) 2005.03.09
Posted by 김용환 '김용환'

댓글을 달아 주세요