Introduction

클래스 템플릿이 다른 클래스 템플릿을 상속 할 경우, 무엇을 주의 하라는지 설명 하고 있다. 클래스 템플릿을 상속 하고 잘못 사용 했을 경우, "가상 함수"가 제 역활을 못할 수 있거나, 컴파일 자체가 되지 않을 수 있으므로, 이 부분은 꼭 봐야 할 것이다.

Content

시작하기에 앞서, 한가지 사실을 미리 알아두어야 한다. 바로 기반이 되는 클래스 템플릿이 파생 되는 클래스 템플릿에 기입 된 파라미터에 종속 될 경우와 종속되지 않을 경우, 이름을 찾는 규칙이 변화 한다는 사실이다.

이 두 경우 중 종속되지 않을 경우(기반 클래스 템플릿이 파생 클래스 템플릿에 기입된 템플릿 파라미터에)가 더 적은 규칙을 가지고 있으므로, 이를 먼저 정리하겠다.

1. 종속되지 않은 기반 클래스일 경우 주의 해야 할 점

종속되지 않은 기반 클래스일 경우, 일반 클래스를 상속 할 때와 거의 똑같다. 다른 점이 있다면, 한정된 이름이 파생 클래스 템플릿에 기입된 템플릿 파라미터 식별자(이름)와 종속되지 않은 기반 클래스에 있는 이름에 같이 있을 경우, 제일 먼저 종속 되지 않는 기반 클래스에 있는 이름을 먼저 찾으므로, 뜻하지 않게 컴파일이 안 될 수 있다.


여기서 봐야 할 것은 d2.strage이 컴파일 되지 않는 것 이다. 왜냐하면 d2.strage는 int 형이기 때문이다. 아무리 템플릿 파라미터로 int* 를 기입하였어도 int로 기입되었다고 한다. 그 이유가 바로, 식별자 "T"를 평가 할 때, 템플릿 파라미터로 평가 된게 아니라 기반 클래스의 "typedef int T"로 평가 되었기 때문이다.

이는 종속되지 않은 기반 클래스에서 먼저 이름을 찾기 때문인 것을 증명한 셈이다. (이름을 중복되지 않게 짓는 습관을 가진 다면, 이러한 문제는 발생 되지 않을 것이다.)

그렇다면
2. 종속된 기반 클래스일 경우 주의 해야 할 점은 무엇인가?
종속되지 않은 기반 클래스일 경우, 그 기반 클래스 부터 이름을 찾는다고 했는데, 여기선 사용하는 식별자가 한정화 되지 않거나, 종속되지 않으면, 종속된 기반 클래스에서 이름 자체를 찾지 않는다. 이것이 다른 점이다.(하지만 MSVC 에선 찾는다. ... 표준하고 다르다..) 그 이유는 이름을 찾을 수 있게 될 경우, 템플릿 특수화로 이름의 상태가 변경(int형 변수에서 열거형 상수로)될 수 있기 때문이라고 한다.



이렇게 이름을 찾을 수 없게 함으로써 우회 할 순 있으나, 그 방법이 있는데, this를 사용하여 한정 시키는 방법과 한정자(::)를 사용하여 한정 시키는 방법, 종속시키는 방법, using을 사용 하는 방법들이 있다.

일반적으로 this를 사용 하는 형태가 더 좋다. 왜냐하면 한정자를 사용하는 방법은 자칫 가상함수 호출을 억제 할 수 있기 때문이다. 그러므로 가상 함수 호출에선 this를 사용하고, 선언같은 경우는 한정자를 사용 하면 된다.


3. using을 사용 할 때 주의 해야 할 점

바로 다중 상속을 할 경우, 동일한 이름이 있을 때, 원하는 것을 정확하게 선택하는 것을 프로그래머의 몫으로 돌리기 때문이다. 인간이 한다는건 언제나 실수를 동반 할 수 있다는 것이기에 주의 해야 한다는 것이다.


Digression

가상함수 호출 때문에 꼭 this를 써야 하는건 분명 기억하고 넘어가야 한다. 이 부분은 g++ 에서 컴파일 할 수 있는 상황을 갖은 사람만이 해당 될려나? 안 배워서 나쁠껀 없지만...

2부 부분이 워낙 문법적인 이야기만 나오기 때문에, 지치는 경향이 있다. 하지만 3부와 4부의 내용을 흡수하기 위해선 꼭 필요한 내용이니 잊어먹어도 좋으니 익숙해 지는것을 포기해서는 안된다. 또 훗날 C++ Template Metaprogramming 을 해야 하므로, 너무 쳐지지 않도록 해야 한다.

이것으로 템플릿 이름 9장은 끝났다.

  • 네이버 블러그 공유하기
  • 네이버 밴드에 공유하기
  • 페이스북 공유하기
  • 라이프코리아트위터 공유하기
  • shared
  • 카카오스토리 공유하기