2012-02-27 200 views
2

我已經從上一學期的一些課程中學習了一些舊的hw任務。 這是打印鏈接列表對象的給定打印功能。 我不明白爲什麼重載的操作符需要兩個參數,一個是操作系統對象。當我們在main.cpp上打印出實際的鏈表對象時,我們並不需要通過一個os對象。另外,它爲什麼返回os?爲什麼我們不能使用cout 而不是「os < <」?重載運算符<< ostream語法

謝謝!

template <class T> 
void List<T>::print(ostream & os) const 
{ 
    os << "<"; 
    ListNode * curr = head; 
    while (curr != NULL) { 
     os << " " << curr->data; 
     curr = curr->next; 
    } 
    os << " >"; 
} 



// overloaded operator<< 
template <class T> 
ostream & operator<<(ostream & os, const List<T> & list) 
{ 
    list.print(os); 
    return os; 
} 

回答

6

順便問一下,問題是如何基本的,我會盡量給出一個非常簡單的(儘管非常非正式的,不那麼迂腐)的答案。

我不明白爲什麼重載運算符有兩個參數 和一個是操作系統對象

操作< <是一個二元運算符。它有一個左側和一個右側。當你寫:

cout << 123; 

要調用這個操作符有兩個操作數(參數):「COUT」在左,一個整數,「123」,在右邊。

當我們打印出main.cpp上的實際鏈表對象時,我們 不需要傳遞os對象。

您的打印功能是類的成員函數或操作符。這會隱含地推斷出,第一個參數粗略地說不需要顯式傳遞,因爲你已經有了'this'指針來處理你的列表對象。對於非成員操作符,情況並非如此,因爲您沒有隱式推導出的「this」對象已經用於左側操作數。

當你寫這樣的代碼:

my_list.print(cout); 

你可以把它看作實際上傳遞兩個參數,「my_list」和「COUT」。即使你沒有明確寫出,你可以通過'this'和其成員訪問'my_list'。這是不是這樣的,如果你寫的打印功能作爲一個非成員,就像這樣:

template <class T> 
void print(const List<T>& my_list, ostream& os); 

這也是與運營商的情況下,這是不是一個成員函數。

此外,它爲什麼返回os?

返回ostream的基準是什麼讓我們寫這樣的語句:

cout << "hello " << "world"; 

首先,我們調用操作< <(COUT,「你好」),然後給了我們另外的ostream參考工作然後讓我們繼續調用運算符< <(cout,「world」)。例如,如果它返回void,那麼它不會允許我們在一個語句中兩次調用該操作符,因爲我們試圖將void作爲左邊的操作數輸出爲「world」。

爲什麼我們不能只用cout而不是「os < <」?

cout基本上實現了ostream接口。所以流,ostringstream,和其他類型的輸出流。通過根據需要的基本接口來編寫,而不是某個特定的ostream衍生產品,您允許您編寫的代碼使用stdio流,文件流,流式流等。基本上它使你的代碼非常通用和可重用,這是你在實際時應該努力去做的事情。在解決多態性概念時,您將更多地瞭解這個主題。

+0

「流流」?這是「串流」的錯字嗎? – 2016-11-01 10:13:57

2

因爲它是一個全局非成員函數。使用成員函數版本,第一個參數隱含地是調用對象this。這意味着你的課程總是必須在左邊。使用非成員函數,它是一個明確的參數;這樣,您可以指定您想要的任何類型,併爲無法修改源的類(只要至少一個參數是用戶定義的類型)重載操作符。

你使用os的原因是它可以處理文件流和任何東西(任何繼承自ostream的東西),而不僅僅是cout

它返回os,以便您可以對返回值執行更多operator<<調用。這使得操作員鏈接,如w << x << y << z,這是operator<<(operator<<(operator<<(w, x), y), z)相同。如果您返回void或其他東西,則必須在w << x處停止,因爲您無法執行任何操作,返回值爲void

0

我不明白爲什麼重載操作符有兩個參數,一個是os對象。當我們在main.cpp上打印出實際的鏈表對象時,我們不需要傳遞一個os對象。

是的,你做的事:當你說cout << x,你逝去的coutxoperator<<

此外,它爲什麼返回os?

使cout << x << y成爲可能。這被解析爲(cout << x) << y,即它將y插入返回值cout << x

爲什麼我們不能只用cout而不是「os < <」?

因爲有時您想輸出到另一個流而不是標準輸出。

0

當我們打印出main.cpp上的實際鏈表對象時,我們 不需要傳遞os對象。

是的,你做了..類似cout << obj;,其中cout是os輸出流。

另外,它爲什麼返回os?爲什麼我們不能只用cout而不是「os < <」?

這使得鏈接:cout << obj << " " << obj2;

爲什麼我們不能只使用,而不是 「OS < <」 COUT?

這將硬連線的輸出流,所以你不能寫入文件或任何其他輸出。