1. 프렌드(friend)


여러분이 알고계시는 friend의 뜻은 무엇인가요? 아시고 계시듯, friend는 "친구"라는 뜻을 가지고 있습니다. C++에서에 friend도 마찬가집니다. 클래스와 클래스끼리 친구(friend)관계를 형성할 수 있습니다. A와 B란 클래스가 존재한다고 합시다. A, B 클래스 둘 다 private 멤버를 가지고 있습니다. 우리가 알고있듯, private 멤버는 외부에서 접근할 수 없습니다. 그런데, A 클래스 내에서 B 클래스를 친구로 지정하면, B 클래스는 A 클래스의 private 멤버에 직접 접근이 가능해집니다. 그러나, A 클래스에서는 B 클래스의 private 멤버에 직접 접근이 불가능합니다. A 클래스도 가능하게 해주기 위해서는, B 클래스 내에서도 A 클래스를 대상으로 친구로 지정해주어야만 합니다. 친구로 지정할때는 friend 선언을 해주어야 하는데, 선언은 friend와 함께 다음과 같이 친구로 정하고 싶은 클래스의 이름을 밝힙니다.

class A {
    friend class B;
    ...
}

위와 같이, friend 선언이 위치하는 영역은 아무곳이라도 상관이 없습니다. private 영역 내에 있거나, public 영역 내에 있어도 아무런 상관이 없습니다. 

#include <iostream>

using namespace std;

class B; // B 클래스가 있다는걸 알림!

class A{
private:
	int adata;
public:
	A(int _data)
	{
		adata = _data;
	}
	void ShowData(B b);
	friend class B;
};

class B{
private:
	int bdata;
public:
	B(int _data)
	{
		bdata = _data;
	}
	void ShowData(A a)
	{
		cout << "a.data: " << a.adata << endl;
	}
	friend class A;
};

void A::ShowData(B b)
{
	cout << "b.data: " << b.bdata << endl;
}

int main()
{
	A a(10);
	B b(20);

	a.ShowData(b);
	b.ShowData(a);
	return 0;
}

결과:

b.data: 20

a.data: 10

계속하려면 아무 키나 누르십시오 . . .


코드를 보시면, 5행에서 "class B;"라고 되어있는데, 이는 B라는 클래스가 있다는걸 알리기 위함입니다. 이 구문을 빼버린다면, 컴파일러는 그런 클래스가 어딨냐며 불만을 표시하게 됩니다. 그이어 7행을 보시면 A라는 클래스가 정의되어 있고, A 클래스 내의 마지막을 보시면 B 클래스를 대상으로 friend 선언한 것이 보이시죠? 이 선언으로 인해 B 클래스에서 A 클래스로 직접 접근이 가능하게 됩니다. 그다음 B 클래스도 A 클래스와 비슷한 구조를 띄고 있습니다. B 클래스 내의 마지막에서도 A 클래스를 대상으로한 friend 선언이 등장하며, 이는 A 클래스에서 B 클래스로 직접 접근이 가능하단 얘기가 됩니다. 


이제, 41~42행을 보시게되면 a란 객체를 만듬과 동시에 생성자로 10이란 값을 넘겨주고, b란 객체를 만듬과 동시에 생성자에게 20이란 값을 건네줍니다. 그럼 a 객체 내의 adata는 10으로 초기화되고, b 객체 내의 bdata는 20으로 초기화 됩니다. 그리고, 44~45행에서 ShowData 함수를 호출하여, 서로의 private 멤버(adata, bdata)에 접근하여 그 값을 출력합니다.


이처럼 friend 선언은 언뜻보면 아무런 이상이 없을것 같지만, 이 friend 선언은 객체지향의 핵심 중 하나인 '정보 은닉'을 깨버리는 행위가 됩니다. 이는 매우 위험하고, friend 선언을 많이 사용하게되면 더 큰 문제를 불러 일으킬수 있습니다. 나중에 연산자 오버로딩을 공부할때 friend 선언이 쓰이나, 그 외에 특별한 경우가 아니고서는 friend의 사용을 자제하셔야 합니다.


오늘 프렌드에 대한 강좌는 여기서 마치도록 하겠습니다. 여기까지 읽느라 수고하셨습니다. 다음 강좌에서는 상속에 대해 알아보도록 하겠습니다.