[펌] 순수 가상 소멸자
Programming/C/C++ / 2010. 5. 6. 14:43
소스를 보다가 소멸자가 순수 가상 함수로 선언 돼 있는데 정의 부분이 있어서 이게 뭔가..싶어서 검색해보고 답을 찾아서 링크..
질문 1]
순수 어쩌고 가상함수. 이렇게 명명되는 함수들은 정의가 없습니다.
그래서 이 함수를 포함하고 있는 클래스는 인스턴스를 만들 수 없죠.
그런데 EC++ (3/e)를 읽다보니 순수 가상 함수에 정의를 하고 있는 부분이 나옵니다.
항목7 93~94페이지에 나온 AWOV 클래스인데요,
class AWOV {
public:
virtual ~AWOV() = 0;
};
이렇게 소멸자가 '순수 가상'으로 되어있음에도 불구하고, 다음 페이지에서
AWOV::~AWOV() {} // 순수 가상 소멸자의 정의
이렇게 정의를 내리고 있습니다.
제가 컴파일을 해보니 또 컴파일도 되더군요-_-; 어떻게 이런 문법이 가능한건가요?
질문 2]
역시 또 EC++(3/e) 항목 31 225페이지에 보면 인터페이스(Java의 그것과 유사한 의미)를 선언하고 있는데요,
class Person {
public:
virtual ~Person();
virtual std::string name() const = 0;
...
};
여기서는 소멸자를 '단순 가상'함수로 선언하고 있습니다.
왜 '순수 가상'으로 만들지 않는 것인지 의문이 생깁니다.
이 클래스는 '추상 클래스'가 아닌 '인터페이스'로 쓸 것인데 말이죠...
구글링 등 검색을 해봐도 만족할 만한 답변을 얻을 수 없어서 질문 드립니다~
질문도 그렇고 답변도 좀 길 듯하여^^ 별도의 답글로 달아 봤습니다.
질문 1에 대한 답변
C++에서 순수 가상 함수의 기계적 의미는 해당 추상 클래스의 vtbl에서 그 순수 가상 함수의 포인터가 0(=null)로 들어 있다는 것입니다. 즉, AWOV 클래스가 이렇게 되어 있다면,
class AWOV { public: virtual ~AWOV()=0; virtual foo(); };
이 클래스의 vtbl은 다음과 같이 나옵니다.
vptr -> [ 0 ] // 첫째 : AWOV::~AWOV()의 주소
[ &(AWOV::foo)] // 둘째 : AWOV::foo()의 주소
하지만, 가상 소멸자의 호출 매커니즘은 파생 클래스의 소멸자가 기본 클래스의 그것을 직접 호출하도록 (컴파일러에 의해) 만들어집니다. vtbl을 통하지 않는다는 것이죠. 따라서 AWOV::~AWOV의 본문이 정의되어 있지 않으면 링크 에러를 내게 됩니다. 이것은 "이렇게 해도 컴파일이 되네" 수준이 아니라 "꼭 이렇게 해야 합니다"라는 의무 조항입니다.
질문 2에 대한 답변
설계상의 선택사항입니다. 순수 가상 함수로 만들 다른 함수가 있으면 구태여 소멸자를 순수 가상으로 만들 필요 없이 비순수 가상으로 만들어도 됩니다.
출처 : http://www.kwak101.pe.kr/bbs/view.php?id=kwk_worksBBS&page=1&sn1=&divpage=1&sn=off&ss=on&sc=on&select_arrange=headnum&desc=asc&no=157
반응형
'Programming > C/C++' 카테고리의 다른 글
[펌] assert 문 사용하기 (0) | 2010.05.13 |
---|---|
[펌] try-catch 예외처리 비용? (0) | 2010.05.13 |
C/C++에서 assert (0) | 2010.05.03 |
TCHAR에 관한여... (0) | 2010.04.29 |
[C]#pragma - once, pack, warning, comment, link (0) | 2010.04.16 |