2011-05-04 159 views
4

從「Thinking in C++ Volume 2」中的Thinking in Depth章節看到,如果您在模板類中具有友好的功能,則需要轉發聲明該功能。我提出這個例子來測試,overlaoding輸出操作:模板和朋友

#include <iostream> 
using namespace std; 
/* 
template<class T> 
class X; 
template<class T> 
ostream& operator << (ostream& os, const X<T>& x); 
*/ 
template<class T> 
class X { 
    T t; 
public: 
    X(T i): t(i) {} 
    friend ostream& operator << (ostream& os, const X<T>& x) 
     { 
      return os << x.t; 
     } 
}; 


int main() 
{ 
    X<int> a(1); 
    cout << a; 
    return 0; 
} 

但它的工作原理沒有提前聲明,但後來我的< <外部類的定義測試:

friend ostream& operator << <>(ostream& os, const X<T>& x); (inside of the class) 

template<class T> 
ostream& operator << (ostream& os, const X<T>& x) 
{ 
     return os << x.t; 
} 

我不確定爲什麼在類中定義它不適用,是因爲你必須明確說ostream操作符函數是一個模板? (使用<>)?

對不起,我感到困惑。

+1

C++ FAQ Lite也有這方面的一章:http://www.parashift.com/c++-faq-lite/templates.html#faq-35.16 – Cubbi 2011-05-04 21:06:59

+0

@ Cubbi:哦,所以當我定義它時在班級裏面,沒有必要提前申報,完美的探索,謝謝:) – Kobe 2011-05-04 21:11:36

回答

2

因爲我的評論似乎令人滿意,所以這是一個答案。

C++ FAQ Lite有a chapter on this,爲了完整起見,可以歸結爲兩種可能的方式來說服編譯器,它在檢查類X的主體時,朋友函數operator<<實際上是一個函數模板。

正如你所做的那樣,一種方法是在類定義之前聲明函數模板operator<<,並在類體內的朋友行中使用<>,給出了operator << <>(的顯着語法。

另一種方法是在類X的主體內部定義好友模板函數的整個主體,這使得不需要前向聲明。