Skip to main content
How to use a pointer variable and null pointer

포인터 변수 사용 방법

포인터 변수 선언 방법

데이터타입 *포인터변수명; (int *ptr;)
or
데이터타입* 포인터변수명; (int* ptr;)

포인터 변수 선언 시 프로그래머의 취향에 따라 별표(*)가 포인터 변수명에 혹은 데이터 타입에 붙을 수도 있습니다.

포인터의 데이터 타입은 포인터 변수가 저장한 메모리 주소가 가리키는 변수의 데이터 타입과 같아야 합니다.

int num = 10;
int *ptr = #
printf("%d", *ptr);

위 예제에서 보는 것과 같이 ptr 포인터 변수의 데이터 타입은 int로 선언했습니다. 그 이유는 ptr이 저장하는 메모리 주소가 가리키는 변수의 데이터 타입이 int이기 때문입니다.

데이터 타입을 void로 선언하면 어떠한 타입도 저장 가능하나 자주 사용되지는 않습니다.

int *ip     // int 변수를 가리키는 포인터
float *fp;  // float 변수를 가리키는 포인터
double *dp; // double 변수를 가리키는 포인터
char *cp;   // char 변수를 가리키는 포인터

포인터 선언 시의 별표(*)와 값을 가져오기 위한 별표(*) 차이점?

포인터를 처음 접할 때 많이 헷갈리는 것이 별표(*) 가 포인터 변수 선언 시에도 사용되고 값을 가져오기 위해서 사용된다는 것입니다.

이것은 모양만 같을 뿐 전혀 다른 의미입니다.

선언 시에 사용되는 별표(*)는 변수가 포인터라는 것을 알려주는 역활이고 값을 가져오기 사용되는 별표(*)는 포인터가 가리키는 값을 역참조한다는 의미입니다.

int *ptr;                // 포인터. 포인터를 선언할 때 *
printf("%d\n", *ptr);    // 역참조. 포인터에 사용할 때 *

포인터 변수 초기화

초기화는 메모리 주소를 포인터 변수에 저장하는 과정입니다. 또한 포인터 변수는 같은 데이터 타입의 변수의 주소 값만을 저장할 수 있습니다.

주소 연산자 &를 통해서 변수의 주소값을 가져올 수 있습니다.

#include<stdio.h>
    
void main()
{
    int a = 10;
    int *ptr;       //포인터 선언
    ptr = &a;       //포인터 초기화
}

포인터 변수는 항상 같은 데이터 타입을 가진 변수를 최종적으로 가르킵니다.

#include<stdio.h>

void main()
{
    float a;
    int *ptr;
    ptr = &a;       //에러, 타입 불일치
}

만약 선언시 포인터 변수에 할당 할 변수의 주소가 확실하지 않은 경우에는 널(NULL) 값으로 초기화 하는 것을 권장합니다. 이렇게 NULL 값으로 초기화된 포인터 변수를 널(NULL) 포인터라 합니다.

#include <stdio.h>

int main() 
{
    int *ptr = NULL;
    return 0;
}

포인터의 사용 또는 포인터의 역참조

포인터 변수에 저장된 메모리 주소가 가리키는 변수의 값을 가져오는 것을 포인터의 사용 혹은 역참조라고 합니다. 여기서 역참조 연산자 *를 사용합니다.

위에서 언급했지만 포인터 변수 선언시의 *와는 다른 의미입니다.

#include <stdio.h>

int main()
{
    int a, *p;  // 변수 그리고 포인터 변수 선언
    a = 10;
    p = &a;     // 포인터 변수 초기화

    printf("%d\n", *p);  

    printf("%d\n", *&a);

    printf("%u\n", &a);

    printf("%u\n", p);

    printf("%u\n", &p);
    
    return 0;
}

OUTPUT
10
10                                                        
3622046324
3622046324
3622046328

printf(“%d”, p);
역참조 연산자()를 사용하여 p가 가르키는 a의 실질적인 값 10 출력

printf(“%d\n”, *&a);
a변수의 주소 값을 리턴(&) 후 그 주소 값이 가르키는 값(*)을 출력하므로 결국 자신의 값 10 출력

printf(“%u\n”, &a);
주소값을 리턴하는 주소 연산자(&)를 사용했으므로 a 주소 값 출력

printf(“%u\n”, p);
포인터 변수 p는 a의 주소값을 가지고 있으므로 a 주소 값 출력

printf(“%u\n”, &p);
포인터 변수 p 자체에 주소 연산자(&)를 사용했으므로 포인터 변수의 자체의 주소 값 출력

포인터 사용 정리

  1. 포인터 변수 선언시의 *는 해당 변수가 포인터 변수임을 알려주는 역활을 합니다.
  2. 모든 변수의 주소를 얻기 위해서는 변수명 앞에 &를 붙여 줍니다.
  3. 포인터 변수는 변수의 주소를 저장합니다. 선언시 int *a는 a가 정수 값을 가진다는 의미가 아닙니다. 이것은 a가 정수 값을 저장하는 변수의 주소를 저장한다는 의미입니다.
  4. 포인터 변수에 의해 저장된 주소 값에 액세스하려면 *가 사용됩니다. 여기서 *는 역참조 연산자입니다.
#include <stdio.h>

int main()
{
    int i = 10; // 10을 저장하는 정수 변수
    int *a;     // 포인터 변수 a 선언

    /*
        포인터 변수 a에 i의 주소값을 저장    
    */
    a = &i;

    /* 
        a는 결국 i의 주소값을 가지고 있으므로 i 변수의 주소값을 출력
    */
   printf("Address of variable i is %u\n", a);

    /*
        역참조 연산자를 사용하여 a가 가르키는 변수의 값 출력
    */
   printf("Value at the address, which is stored by pointer variable a is %d\n", *a);

   return 0;
}

OUTPUT
Address of variable i is 1169914348
Value at the address, which is stored by pointer variable a is 10
<< 다음 혼자 공부하는 C언어 이전 >>

댓글 남기기

이메일은 공개되지 않습니다. 필수 입력창은 * 로 표시되어 있습니다