참조변수와 포인터는 같은 것일까

종종 우리는 참조변수와 포인터를 동급으로 취급한다. 객체지향언어에서 다형성의 정의는 다음과 같다. ‘다형성은 기반 클래스의 참조변수로 여러 파생 클래스의 객체를 가리키는 것’. 그리고 그에 대한 예시로 우리는 포인터를 쓴다.

#include <iostream>

class A
{
	public:
		virtual void say(void) {std::cout << "A" << std::endl;}
};

class B : public A
{
	public:
		void say(void) {std::cout << "B" << std::endl;}
};

int main(void)
{
	A *pointer = new B();
	pointer->say();
	return (0);
}

다형성의 정의에서 ‘참조변수’ 라는 키워드가 등장하는데, 예제 코드에서는 포인터를 사용한다. 위 코드의 작성자는 참조변수와 포인터를 동급으로 취급하고 있는 것이다.

이상한 일이다. 실제로 ‘참조변수’ 와 ‘포인터’ 는 서로 다른 개념이다. 사용하는 방식, 키워드 그리고 모양새가 다르다. 그러나 많은 사람들이 이 둘을 때로는 같게, 때로는 다르다고 말한다. 나는 이 둘을 어떻게 다루어야 하는 것인가?

참조변수에 대해 알아보자

참조변수에 대해 알아보기 전에 몇 가지 단어에 대해 정의를 하고 시작하자. 먼저 ‘변수’ 는 할당된 메모리 공간의 이름이다. 우리는 이 ‘이름’ 을 가지고 해당 메모리 공간에 접근한다. 간단한 예시는 다음과 같다.

int a; // 메모리 공간이 생겼고, a 라는 이름이 붙었다.
a = 10; // a 공간에 접근해서 10 이라는 값을 채웠다.

‘참조자’ 는 할당된 메모리 공간에 또 다른 ‘이름’ 을 붙이는 기능을 한다. 어떤 변수가 참조하는 공간의 또 다른 이름을 붙이는 것이다. 이에 대한 예시는 다음과 같다.

int a = 10; // a 라 불리는 메모리 공간이 생겼고, 10으로 초기화 되었다.
int **&**ref = a; // a 라 불리는 메모리 공간의 또 다른 이름 ref 이 선언과 동시에 초기화 됨.