포인터 변수 사용 방법
반응형

포인터 변수 선언 방법

int *ptr;

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);
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 자체에 주소 연산자(&)를 사용했으므로 포인터 변수의 자체의 주소 값 출력

포인터 사용 정리

  • 포인터 변수 선언시의 *는 해당 변수가 포인터 변수임을 알려주는 역활을 합니다.
  • 모든 변수의 주소를 얻기 위해서는 변수명 앞에 &를 붙여 줍니다.
  • 포인터 변수는 변수의 주소를 저장합니다. 선언시 int *a는 a가 정수 값을 가진다는 의미가 아닙니다. 이것은 a가 정수 값을 저장하는 변수의 주소를 저장한다는 의미입니다.
  • 포인터 변수에 의해 저장된 주소 값에 액세스하려면 *가 사용됩니다. 여기서 *는 역참조 연산자입니다.
#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언어 이전 >>
반응형

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

포인터 그리고 배열  (0) 2019.12.20
C언어 이중 포인터  (0) 2019.12.20
C언어 포인터  (0) 2019.12.20
C언어 공용체 (Union)  (0) 2019.12.20
typedef 별칭(Alias) 주기  (0) 2019.12.19