程序師世界是廣大編程愛好者互助、分享、學習的平台,程序師世界有你更精彩!
首頁
編程語言
C語言|JAVA編程
Python編程
網頁編程
ASP編程|PHP編程
JSP編程
數據庫知識
MYSQL數據庫|SqlServer數據庫
Oracle數據庫|DB2數據庫
 程式師世界 >> 編程語言 >> C語言 >> C++ >> C++入門知識 >> 避免重載&&(邏輯與)、||(邏輯或)或,(逗號)操作符

避免重載&&(邏輯與)、||(邏輯或)或,(逗號)操作符

編輯:C++入門知識

這幾天讀《C++編程規范http://book.douban.com/subject/1459007/》讀到第30條:“避免重載&&、||或,(逗號)”,一直不能完全吃透。今天才理解,原來是這麼回事:
 
  內建的&&(邏輯與)、||(邏輯或)和,(逗號)操作符總是滿足以下性質:
從左至右對操作數進行求值;
對於&&操作符,若左操作數為假,那麼右操作數將不會求值,所以我們可以放心地寫下
[cpp]
if (p && p->next) 
這樣的代碼而不用擔心p為0時p->next會先被求值;
類似地,對於||操作符,若左操作數為真,那麼右操作數將不會被求值。
 
  上面第2點和第3點又叫做“短路求值法(Short Circut Evaluation)”。
 
  如果我們重載了這三個運算符,會發生什麼呢?事實上,當一個操作符被重載時,編譯器就會將該操作符視為一個函數,而不是一個真正的操作符。一個函數的參數總是會被全部求值,而且其求值順序是未定義的。因此上述三個性質就全都不能滿足了!
 
  考慮下面這個程序:
 
[cpp]
#include <iostream> 
#include <string> 
 
using namespace std; 
 
string retString() 

    cout << "string" << endl; 
    return "hello"; 

 
int retInt() 

    cout << "int" << endl; 
    return 47; 

 
int main() 

    retInt(), retString(); 

 
  不管用什麼編譯器,只要其支持C++標准,程序的輸出都應該為
 
int
string
 
  但如果重載了逗號操作符,像下面這樣:
[cpp]
void operator , (int a, const string &b) 


 
  用VS2010編譯後,程序就會先輸出string,再輸出int,可見操作數是從右向左求值的。
 
  而如果對重載定義做少許的改動:
 
[cpp]
void operator , (const int &a, const string &b) 


 
  也就是把左操作數a的定義變成常量引用。那麼程序又會先輸出int再輸出string了。你可能會懷疑此時程序調用的是內建逗號操作符,那麼可以在重載定義中加一條cout輸出語句,就知道調用的其實還是重載操作符。只不過把參數的定義改了改,參數的求值順序就變了,是不是很“神奇”?



摘自 子子翔的專欄

  1. 上一頁:
  2. 下一頁:
Copyright © 程式師世界 All Rights Reserved