본문 바로가기

Academy I/Tech Academy

A Beginner's Guide to Pointers

1 포인터란?

포인터는 기본적으로 다른 변수와 동일한 새로운 타입의 변수다. 다른 변수들이 실 데이터를 가지고 있는 것 대신에 데이터가 저장된 메모리 공간의 주소를 가지고 있다는 점에 있어서 차이가 있다.

데이터가 저장된 메모리 공간의 주소, 즉 위치정보를 가지고 있다는 것은 매우 단순한 개념같지만, 매우 중요한 개념이기도 하다.

C와 C++로 디자인된 링크드리스트(:12), 트리 와 같은 자료구조(:12)들이 포인터 개념을 기반으로 하고 있다. Perl, Java(:12)와 같이 포인터 대신 레퍼런스 개념을 가진 언어들이라 할지라도 기본개념에 있어서 포인터와 별 차이가 없음을 알 수 있다.

(역주: 포인터에 대해서 좀더 쉬운 수준에서 접근하길 원한다면, Java와 함께 하는 컴퓨터 과학 3장Spim 1-3장, 1-2장문서를 참고하기 바란다. 이들 문서를 가볍게 읽는 정도로 포인터의 개념을 잡기가 한층 수월해 질 것이다.)

1.1 시작

어떻게 포인터를 정의할 수 있나.
변수이름에 별표(*)를 붙이는 것을 제외하곤 다른변수와 동일하다.

예를들어보자, 아래의 두개는 둘다 int형 포인터 포인터를 만들어준다 :
int* pNumberOne;
int* pNumberTwo;

두 변수의 이름을 보면 앞에 공통적으로 문자p가 붙어있는걸 알 수 있다. 이건 이 변수가 pointer 형이라는 것을 다른 개발자가 쉽게 인지할 수 있도록 하기 위한 일종의 풍습이다.


반드시 이 규칙을 따를 필요는 없다. p_를 붙여도 되고 P를 붙여도 될 것이다. 어쨋든 표준적인 룰을 만들어서 사용하면 된다. 이는 소스 프로그램의 가독성을 높여준다는 점에서 매우 중요한 일이다.


위 선언에서 포인터 변수임을 알려주기 위해서 *가 사용되고 있음을 알 수 있다.

이제, 만들어진 포인터로 무언가를 해보자 :
pNumberOne = &some_number;
pNumberTwo = &some_other_number;
&기호는 'the address of' 라고 읽을 수 있다. 그리고 변수자신을 대신해 메모리 주소를 되돌려준다. 즉 위의 코드는 some_number의 메모리 주소를 pNumberOne에 대입(혹은 저장)하겠다는 의미가 된다. pNumberOne에는 some_number의 주소가 들어 있는 것이다.

만약 우리가 some_number의 주소를 참조해서 값을 읽어들이거나 변경하길 원한다면 pNumberOne을 이용하면 된다. pNumberOne은 some_number의 주소를 가리키고 있기 때문이다. 만약 pNumberOne으로부터 some_number의 값 (Value)즉 주소가 가리키고 있는 메모리에 저장된 값을 참조하기 원한다면 *를 이용해서 *pNumberOne으로 사용하면 된다.

1.2 배운걸 확인해 보자

만약 앞의 내용을 이해하지 못했다면, 포기하기 전에 이 예제를 읽어보기를 추천한다. 밑의 코드를 보면 포인터를 좀더 쉽게 이해할 수 있을 것이다.

#include <stdio.h>

void main()
{
    // 변수의 선언
    int nNumber;
    int *pPointer;

    // 이제, 변수를 대입한다
    nNumber = 15;
    pPointer = &nNumber;

    // nNumber로부터 변수를 출력해준다:
    printf("nNumber is equal to : %dn", nNumber);

    // 이제, pPointer를 통해 nNumber를 바꿔보자:
    *pPointer = 25;

    // 위 명령으로 인해 nNumber가 변경의 결과를 증명하기위해
    // 변수를 다시 출력한다:
    printf("nNumber is equal to : %dn", nNumber);
}
위의 코드를 생각하면 읽어보고, 값을 미리 예측한 후 컴파일 해서 실행시켜 보도록 하자.

예측한대로 값이 나오지 않은다면, 코드를 이해하고 예측이 가능할 때까지, 계속 읽고 계속 실행해 보기 바란다.

1.3 함정!

아래의 코드에는 문제가 숨어 있다. 찾아보자.
#include <stdio.h>

int *pPointer;

void SomeFunction();
{
    int nNumber;
    nNumber = 25;    

    // pPointer 포인터에 nNumber을 만들어준다:
    pPointer = &nNumber;
}

void main()
{
    SomeFunction(); // pPointer 주소에 무언가 만들어준다

    // 왜 실패하는가!?
    printf("Value of *pPointer: %dn", *pPointer);
}

위 프로그램은 잘못된 프로그램으로, 꽤나 심각한 문제를 가지고 있다. 주석에는 실패한다고 말하고 있지만 많은 경우 '제대로 작동되는 것처럼 ' 보이기 때문이다. 여튼 위 프로그램은 결정적인 문제가 있다.

프로그램은 SomeFunction함수를 호출하고, nNumber변수를 생성한후에 pPointer 에 대입한다. 이제 pPointer은 nNumber의 주소를 가리키게 될 것이다.

하지만 nNumber은 지역변수이기 때문에 함수를 빠져나갈 때 사라진다는 문제점이 있다.

지역변수는 항상 선언한 그 블럭에서 이용되고 빠져나갈때 지워진다. 이것은 매우 중요한 개념인데, 이것을 이해하려면, 프로세스가 명령을 어떻게 스택에 유지하는지에 대한 것을 알고 있어야 한다. 이에 대한 자세한 내용을 알기를 원한다면 어셈블리 프로그래밍 - 함수편을 읽어보기 바란다. 굳이 깊이 알고 싶지 않다면, 우선은 지역변수는 해당 함수에서만 유효하다는 것을 인지하는 수준에서 넘어가도록 한다.

이제 문제를 알았으니 문제를 풀어야 할 것이다. 이 문제를 풀기 위해서는 메모리 할당과 관련된 기술을 알고 있어야 한다.

1.4 동적 할당

동적 할당은 포인터를 사용함으로써 발생하는 문제를 해결하기 위한 중요한 개념이며, 포인터와 함께 필수로 사용된다.

동적 할당은 동적_메모리_할당(:12)의 줄임말이다. 즉 사용가능한 메모리를 할당하는 기술이라고 보면 된다. 사용가능한 메모리를 공간을 할당 받았다면, 도대체 그 메모리 공간이 어디에 있는지에 대한 정보를 알고 있어야 할것이다.

당신의 컴퓨터가 1G의 메모리를 가지고 있고, 여기에서 1메가의 공간을
동적으로 할당받았다면, 그 1메가의 공간이 1G의 공간중 어디에 있는지를 알아야 사용할 수 있는 것이다. 다행히 우리는 메모리가 할당된 곳의 시작주소를 알 수 있으며, 이 주소를 사용하기 위한 포인터도 알고 있다.

비록 개념이 많이 햇갈릴 수 있겟지만 , 매우 간단하다. 아래코드는 integer 메모리를 할당하는 것을 보여준다.
int *pNumber;
pNumber = (int *)malloc(1000*sizeof(int));
  1. 포인터형 변수인 pNumber를 선언한다.
  2. malloc(2)함수를 호출해서 int형 데이터를 1000개 저장할 수 있는 메모리 공간을 할당하고, 할당된 메모리 공간의 시작주소를 pNumber에 저장한다.
  3. 1000 * 4 == 4000byte 가 할당된다.

C++은 new라는 키워드를 이용해서 좀 더 직관적으로 메모리 할당이 가능하다. 동일한 일을 하는 C++버전의 코드다. 앞으로는 C++을 기준으로 설명하도록 하겠다.
int *pNumber;
pNumber = new pNumber(1000);

아래는 double 버젼의 메모리 할당 코드다.
double *pDouble;
pDouble = new double;

이식은 같은형식이다, // 해석 바람 -> so you can't really fail with this bit.

동적할당이 선언된 지역 변수들과 다른건, 아무리 함수에서 빠져나오거나( return 하였을 경우 ), 선언한 블럭을 빠져나올때( {} Scope 를 벗어났을 경우 )에도 할당한 메모리가 지워지지 않는다는 것이다.

그래서 만약 동적할당을 이용해 이 예제를 다시 쓸려고 한다면, 다음과 같이 작성할 수 있다.

#include <stdio.h>

int *pPointer;

void SomeFunction()
{
    // pPointer 포인터에 new integer를 만든다
    pPointer = new int;
    *pPointer = 25;
}

void main()
{
    SomeFunction(); // pPointer 포인터에 무언가를 만들어준다
    printf("Value of *pPointer: %dn", *pPointer);
}

생각하면서 읽어보고, 컴파일러가 어떻게 할지 생각해보고, 왜 이렇게 나오는지 이해해 봐야 한다.

SomeFunction이 호출될때, 메모리를 할당하고 pPointer 포인터에 할당한 메모리의 주소를 넘긴다. 함수가 리턴될때, 새로운 메모리는 원래대로 남아있으므로 pPointer는 이용할 수 있게 되는것이다. 동적할당은 바로 이런 것이다! 왜 이 코드는 에러가 일어나지 않는지 생각해봐라.

1.5 메모리의 할당과 해제

이 문제는 매우 쉽게 고칠 수 있는 문제일 수도, 복잡할 수도 있다. 그래도 명심해야 하는 것은 이 문제는 매우 중요하다 라는 것이다. 우선 생각해봐야 될 문제는 동적할당을 이용하여 할당해놓은 메모리를 사용 후에도 그냥 놔둬버리는 점이다. 이 할당된 메모리는 실제 자동적으로 제거되지 않으므로 '메모리 누수' 가 생기게 되는 것이다.

심지어 프로그램이 끝났을 때에도 컴퓨터는 메모리는 할당된 채로 남기게 된다. 이 문제는 컴퓨터에게 메모리 사용이 끝날때 알려주지 않는다면, 다른 프로그램이 이 메모리를 사용할 수 없으므로 메모리의 낭비가 일어날 것이고 만약 모든 메모리를 써버리게 되면 시스템 충돌을 일어낼 것이다, 그래서 이것은 매우 중요한 문제이다.

다음은 프로그램이 종료되었을때 메모리를 해제해주는 매우 간단한 예제이다

delete pPointer;

간단해 보이지만 이것이 전부다. 하지만 해제하려고 할 때에는 할당을 한 시점에 pPointer 변수에 확실한 pointer를 넘겨주었는지 체크를 해야한다. 쓰레기 값이 들어있음으로 인해 위험할 수도 있지만, 메모리 해제를 함으로써 프로그램은 보다 효율적이고 완벽하게 된다.

좀 더 발전하여 메모리를 낭비하지 않는 코드로 작성된 예제를 다시 보자.

#include <stdio.h>

int *pPointer;

void SomeFunction()
{
// pPointer 포인터에 new interger 를 만들어준다
    pPointer = new int;
    *pPointer = 25;
}

void main()
{
    SomeFunction(); // pPointer 포인터에 무언가를 만들어준다
    printf("Value of *pPointer: %dn", *pPointer);

    delete pPointer;
}

전체에서 추가된 줄은 한 줄이지만 이 줄은 가장 중요한 줄이다. 만약 메모리를 해제하지 않는다면, '메모리 누수' 현상이 일어 날 것이고, 프로그램이 종료되기 전까지는 이 현상은 반복될 것이다.

1.6 함수로 포인터 전달하기

포인터를 함수인자로 전달하는 기술은 매우 유용하고, 매우 쉽게 마스터할 수 있다. 만약 프로그램에서 수를 가져가 5를 더하고 싶다면, 우리는 다음과 같이 작성할 수 있을 것이다.

#include <stdio.h>

void AddFive(int Number)
{
    Number = Number + 5;
}

void main()
{
    int nMyNumber = 18;
    
    printf("My original number is %dn", nMyNumber);
    AddFive(nMyNumber);
    printf("My new number is %dn", nMyNumber);
}

그러나 문제는 이 Number 참조로 Addfive함수의 인자로 nMyNumber를 넘겨줄 때, 변수 그자체가 아니라는 점에 있다. 그런 까닭에 'Number = Number + 5' 이줄은 복사된 변수 Number에 5가 더해진다, 원래 변수는 in main() 안에 남겨두니 영향이 없다. 실행을 해보면 결과값을 알 수 있을것이다.

이러한 문제를 가지고 있을때에는, 변수의 포인터를 넘겨줘서 함수에서 그 메모리를 계속하여 수정할 수 있다.

즉 Number 가 아닌 Number 의 포인터임을 생각하고 함수의 원형을 바꾸어 주어야 한다. 바꾸어 주어야 할 점은 void AddFive(int Number)이 void AddFive(int* Number) 이렇게 * 를 붙여 바꾸어 준다는 것이다.

프로그램을 조금 바꿔 다시 작성해보자. 그럼 Number 포인터변수에 nMyNumber의 포인터가 넘어오는가?

pointer를 인자로 전달하기 위해서는 변수의 앞에 &기호를 붙여서 넘겨준다, 우리가 다시 부를때
the address of 라고 읽는다.

#include <stdio.h>
void AddFive(int* Number)
{
    *Number = *Number + 5;
}

void main()
{
    int nMyNumber = 18;
    
    printf("My original number is %dn", nMyNumber);
    AddFive(&nMyNumber);
    printf("My new number is %dn", nMyNumber);
}

코드를 작성하여 실행을 해보고 완전한 당신의 것으로 만들어야 한다. 그럼 여기서 질문해 보겠다. AddFive 함수안에 Number 앞에 *가 중요한가?

답은 이 *이 Number변수에 저장된 pointer 이 자신에 5를 더하는 게 아닌, Number 변수에 저장된 pointer 가 가르키는 곳의 숫자에 5를 더하라는 것을 컴퓨터에게 알려주기 때문에 필요하다는 것이다.

마지막으로 생각해줘야 할 것은 리턴형을 포인터로 주고 싶다면 다음과 같이 해야될 것이다 :

int * MyFunction();

이 예제는 MyFunction 리턴값이 integer형 포인터이다.

1.7 클래스 포인터

여기서 말할 것은 여러개의 변수나 함수가 있는것을 구조체나 클래스로 묶어 포인터로 이용하는 것이다.

class 선언은 다음과 같다.

class MyClass
{
public:
    int m_Number;
    char m_Character;
};

그리고 MyClass타입 변수를 다음과 같이 선언한다.

MyClass thing;

만약 이것을 모르겠다면, 윗 부분부터 다시 읽어보길 바란다.

MyClass 포인터 변수의 선언은 다음과 같이 한다 :

MyClass *thing;

이렇게 하면 포인터 변수가 선언된다. 그리고, 당신은 메모리를 할당한 다음에 pointer 변수에 넘겨줘야 할 것이다.

thing = new MyClass;

이렇게 하면 생기는 문제는 '어떻게 포인터를 이용할 것인가?' 이다. 보통 class 의 멤버에 접근하기 위해서는 thing.m_Number 라고 쓸 것이다. 하지만 이 접근 방법은 제대로 된 것이 아니다. 왜냐하면 thing 포인터 변수는 실제 객체가 아닌 포인터이기 때문이다. m_Number 변수를 불러올 수 있게 해보자.

이것은 m_Number를 가지고 있는 구조체이고, 그 점 때문에 조금 다른 규칙을 이용해야 한다.

.
(dot) 을 ->(dash 뒤에 > 크다 라는 기호를 붙인 기호)로 바꾸고 바꾼 예제를 보자.

class MyClass
{
public:
    int m_Number;
    char m_Character;
};

void main()
{
    MyClass *pPointer;
    pPointer = new MyClass;

    pPointer->m_Number = 10;
    pPointer->m_Character = 's';

    delete pPointer;
}

1.8 배열의 포인터

위에서 설명한것들 뿐만 아니라 배열을 가르키는 주소 포인터 또한 만들 수 있다, 이 예제를 보자.

int *pArray;
pArray = new int[6];

이것은 pArray 포인터를 생성하고 6개의 요소를 가진 배열의 주소로 만들어준다. 동적할당을 이용하지 않고 다른방법으로 할 수도 있다.

int *pArray;
int MyArray[6];
pArray = &MyArray[0];

이것은 &MyArryay[0]로 쓸수도 있고, 간단히 MyArray를 쓸 수도 있다. 이것은 단지 배열을 적용시키는 c/c++언어의 방법일뿐이다

일반적인 함정은 pArray = &Myarray; 로 쓰는것인데 이것은 올바르지 않는 표현이다. 만약 이렇게 썼다면, (타입이 없는) 배열의 주소를 가르키는 포인터로 써버릴 것이다, 이 표현은 원하는 대로 작동하지 않을 것이다.

1.9 배열의 포인터 이용하기

만약 배열의 포인터를 가지게 되었다면, 어떻게 이것을 이용해야 될까?

자, int형의 배열을 가진 포인터를 말해보아라.

포인터는 초기화된 배열을 처음부터 가지고 있을 것이다, 아래 예제를 보자 :

#include <stdio.h>

void main()
{
    int Array[3];
    Array[0] = 10;
    Array[1] = 20;
    Array[2] = 30;

    int *pArray;
    pArray = &Array[0];

    printf("pArray points to the value %dn", *pArray);
}

만들어진 포인터가 배열에서 다른 요소를 가리키게 하고 싶다면, pArray++ 라고 하면 된다. 그럼 이제 pArray + 1 과 같은 pArray++ 과 비슷한 pArryay + 2 를 추측할 수 있을것이다, 이것은 포인터를 배열의 요소를 두번째 옴겨줄 것이다.

여기서 주의해야할 것은 배열의 범위 (예제에서는 3)을 벗어나면 안된다는 것이다. 왜냐하면 컴파일러는 포인터를 쓸 때 배열의 끝에 왔는지 체크하지 못하기 때문이다. 그럼 쉽게 이 방법을 쓸 수 있을 것이다.

예제를 다시 보자. 우리가 지정한 3개의 변수를 출력해준다 :

#include <stdio.h>

void main()
{
    int Array[3];
    Array[0] = 10;
    Array[1] = 20;
    Array[2] = 30;

    int *pArray;
    pArray = &Array[0];

    printf("pArray points to the value %dn", *pArray);
    pArray++;
    printf("pArray points to the value %dn", *pArray);
    pArray++;
    printf("pArray points to the value %dn", *pArray);
}

pArray 포인터 변수를 뺄 수도 있다. 일반적인 포인터의 pArray로부터 pArray - 2 는 2번째 앞의 요소를 가르킨다. 여기서 더하거나 빼는 것은 포인터 변수이지 배열의 값이 아니다.

포인터의 몇 조작들과 배열의 사용은 대부분 무언가를 찾을때 반복문에서 주로 사용된다.

그리고 포인터의 값도 int* pNumberSet와 같이 가져올 수 있다. 배열을 다루어 보았을 것이다. 만약 포인터를 이용한 배열의 값을 가져올 수도 있다. pNumberSet[0] 는 *pNumberSet와 같은 뜻이다. 그리고 pNumberSet[1]는 *( pNumberSet + 1 ) 와 같은 뜻이다.

배열에서 마지막으로 조심해야할 것은, 만약 배열을 이용하기 위해 new 키워드로 메모리할당을 해주었다면 예제와 같이 해주어야한다.

int *pArray;
pArray = new int[6];
delete [] pArray;

[] 뒤에 있는 배열을 제거해 주겠다는 것이다. 컴파일러에게 지우는 것이 배열이고 하나의 item아니라는것을 말해준다. 만약 이방법을 꼭 이용하지 않는다면 '메모리 누수' 현상이 일어날 것이다.

new 키워드를 이용해서 할당하지 않았다면 메모리 해제를 할 필요가 없다.
void main()
{
    int number;
    int *pNumber = number;
    delete pNumber; // wrong - *pNumber는 new 키워드로 할당되지 않았다
}

2 FAQ

2.1 new와 delete를 쓰려는데 왜 'symbol undefined' 에러가 나나요?

대부분 C++로 작성된 소스코드를 C 컴파일러를 이용해서 컴파일 할때 발생한다. new와 delete 연산자는 C++만이 가지고 있으며, C 컴파일러는 이들 연산자를 인식하지 못한다.

이 문제는 C++컴파일러를 사용하는 것으로 해결할 수 있다.

2.2 new와 malloc이 어떻게 다르나요?

new키워드는 c++ 명세에 포함되어 있다. 그래서 동적메모리를 만드는 표준방법(이외에 윈도우 메모리할당 루틴을 이용하는)이다.

c++ 응용프로그램을 작성하는데 있어서 malloc()를 사용할 필요는 없다. 당신은 c c++ 응용프로그램에서 malloc 의 이용은 절대적으로 필요하지 않는다

왜냐하면 malloc은 c++의 객체지향적인 특징이 아니기 때문이다 new를 이용하면 클래스들을 할당된 메모리는 클래스생성자를 호출해 예방한다, 단지 이하나의 예에서도 문제가 일어난다.

malloc 과 free사용시 일어나는 문제의 결과에서 처럼 malloc의 목적과 의도는 쓸모 없어졌기 때문에 이 글에서 그것에 대한 자세한 이야기들을 다루지 않는다.

이것은 C++의 경우이고 C에서는 여전히 malloc()함수를 이용한 메모리 할당이 중요하게 사용된다.

또한 여러가지 이유로 C++을 사용하더라도 new 대신 malloc를 사용하기도 한다.


2.3 free 와 delete를 같이 사용해도 되나요?

메모리를 할당한 루틴과 동일한 루틴을 사용해서 메모리를 해제해 주어야 한다. 예를들어 free()는 malloc()으로 할당한 메모리를 해제 할때만 유효해, delete는 new로 할당한 메모리의 해제에만 유효하다.

자바쉑키
malloc과 free로 객체 생성/제거 하시면 생성자와 소멸자가 실행되지 않습니다.
또한 malloc과 free는 cpp라이브러리의 일부분이 아닙니다. cpp에서의 사용은 권장되지 않는것 같습니다

2.4 참조

이글은 참조에 대한 내용을 거의 다루고 있지 않다. 그러나, 많은 사람들이 이것에 대해 질문하는 것을 보았다.

간단히 얘기해 보자면 참조는 포인터와 비슷한 목적으로 사용하기 위한 간단한 대안 중에 하나이다.

참조의 개념으로 포인터를 바라본다면,
& 를 'the address of' 라고 읽지않고 'a reference to' 라고 읽을 수 있다.

참조는 포인터와 같다. 자동으로 역참조가 되는 것을 빼고 말이다.

아래의 코드에서 pNumber의 포인터는 myOtherNumber의 포인터와 같다.
int* pNumber = &myOtherNumber;
*pNumber = 25;
포인터와 참조의 다른 차이점이라면 참조는 포인터처럼 나중에 선언을 바꾸지않는 '재지정'하지 않아도 된다는 점이다.

예를 들어 다음코드의 결과는 '20'이 나올 것이다 :
int myFirstNumber = 25;
int mySecondNumber = 20;
int &myReference = myFirstNumber;

myReference = mySecondNumber;

printf("%d", myFristNumber);

클래스일때, 벨류는 다음과 같은 구조에서 참조로 변수를 설정할 수 있다 :

CMyClass::CMyClass(int &variable) : m_MyReferenceInCMyClass(variable)
{
    // 코드를 여기에 작성한다
}

함수라면 다음과 같이 하면 될 것이다.

#include <stdio.h> void e2(int &a) -- 커플님 말에 따라 수정 { a = a * 2; }

 int main() { int value=3; e2(value); printf("%d\n", value); }


3 정리

이 문서를 읽으면 포인터를 이해하는데 어려움을 느끼지 않는 수준에 올라설 수 있을 것이다. 그러나 최소한 두번 이상은 봐야 할 것이다. 많은 사람들이 한번에 이해하기는 힘드리라 생각된다. 다음은 여기에서 다룬 내용중 핵심이라 할 만한 것들이다.

  • 포인터는 메모리영역의 주소를 담는 변수이며 변수이름앞에 * 를 붙이면된다 (예, nt *number)
  • 변수의 주소를 얻고 싶을때는 & 기호를 앞에 붙이면된다 (예, pNumber = &my_numbe).
  • 기호는 선언일때를 제외하고 (int *number 와같은) 'the memory location pointed to by' 라고 읽는다.
  • & 기호는, 선언일때를 제외하고(int &number와같은) 'the address of' 라고 읽는다.
  • 메모리를 할당할때는 'new'키워드를 이용할 수 있다. 객체에 대한 메모리 할당이 아니라면 malloc()를 이용할 수 있다.
  • 포인터는 같은 타입의 포인터에 대해서면 할당되어질 수 있다. 예를들어 int *number 는 class *Myclass를 가리킬 수 없다.
  • 함수를 포인터로 넘길 수도 있다.
  • malloc()로 할당한 메모리는 free()를 new로 할당한 메모리는 delete를 쓴다.
  • 이미 존재하는 배열의 주소를 얻고싶다면 &array[0].
  • 동적할당한 배열을 해제하고 싶다면 delete[] 를 이용해야된다, 그냥 delete를 써선 안된다. new와 delete를 이용해서 객체수준에서 메모리 할당을 다루기 때문에 얻는 편리함이다. 만약 malloc()를 이용해서 2차원배열에 대한 메모리를 할당했다면, 루프를 돌면서 하나하나씩 free()해주어야 할 것이다.

이것은 포인터에 대한 완벽한 가이드가 아니다. 제목그대로 초보자를 위한 간단한 정보들만 담고 있다. 이중포인터와 이들의 응용, 함수포인터들에 대해서는 자세히 다루고 있지 않다.


[출처 : http://www.joinc.co.kr/modules/moniwiki/wiki.php/Site/C/Documents/PointerGuide]


'Academy I > Tech Academy' 카테고리의 다른 글

Pro*C/C++  (0) 2015.01.13
I-Node 링크 파일 찾기  (0) 2015.01.09
gcc 입력과 출력  (0) 2015.01.09
How to use g++  (0) 2015.01.08
ora-28002 7일 안에 암호가 만료  (0) 2015.01.06
pro*C  (0) 2015.01.06
[Linux]file system 사용량 측정하기 (df, du)  (0) 2015.01.02
[Linux]file system 검사하기  (0) 2015.01.02