模板類繼承後找不到父類函數的問題
阿新 • • 發佈:2017-10-23
argument 有關 過程 類繼承 找不到 his cout this 添加
錯誤示例:
1 template<class T> class List 2 { 3 public: 4 void next(T*){ 5 cout<<"Doing some stuff"<<endl; 6 } 7 }; 8 9 template<class T> class Special_List: public List<T> 10 { 11 public: 12 void do_other_stuff(T* item){13 next(item); 14 } 15 }; 16 17 18 int main(int argc, char *argv[]) 19 { 20 Special_List<int> b; 21 int test_int = 3; 22 b.do_other_stuff(&test_int); 23 }
使用g++編譯,出現如下錯誤:
1 template_eg.cpp: In instantiation of ‘void Special_List<T>::do_other_stuff(T*) [with T = int]‘: 2 template_eg.cpp:27:35: required from here 3 template_eg.cpp:18:25: error: ‘next‘ was not declared in this scope, and no declarations were found by argument-dependent lookup at the point of instantiation [-fpermissive] 4 template_eg.cpp:18:25: note: declarations in dependent base ‘List<int>‘ are not found by unqualified lookup 5 template_eg.cpp:18:25: note: use ‘this->next‘ instead
解決方法:
1、
this->next(item)
2、
List<T>::next(item)
3、
1 template<class T> class Special_List: public List<T> 2 { 3 using List<T>::next; 4 public: 5 void do_other_stuff(T* item){ 6 next(item); 7 } 8 };
具體原因:
模板的處理過程分為兩步(標準編譯,VS是另一種方式)。第一步,在類型實例化前,所有不依賴於模板參數的數據被查找和檢查。第二部,類型確定,而後處理剩余的部分。
現在,在第一階段,沒有跡象表明next函數是依賴於模板參數的,因此它需要再類型例化前被處理。但是基類型是被當前模板例化的,且並不知道類型T會被例化成怎樣的類,編譯器無法進入基類中查找。
而this->next則將next加入了依賴模板的函數名單,這使得編譯器會在第二階段才查找next函數的實現,這時T是已知類型,基類List<T>也是已知的,編譯器可以進入查找。
在處理的第二階段,查找表只會查找參數依賴表中的函數並添加進表中。如果next函數是一個與T有關的namespace中,那麽它會被查找添加,而如果它僅是基類的一個成員函數,那麽它對於ADL是不可見的。對於next函數,編譯器需要在查找表中檢索next,而對於this->next,編譯器查找的是this(在第二階段模板類型例化後),之後才會查找next。
ADL(參數依賴查找,Argument-dependent lookup):http://www.cnblogs.com/zl1991/p/7718718.html
模板類繼承後找不到父類函數的問題