過載操作符的限制

2021-04-12 19:41:16 字數 3296 閱讀 9043

與c一樣,c++使用布林表示式短路求值法(short-circuit evaluation)。這表示一旦確定了布林表示式的真假值,即使還有部分表示式沒有被測試,布林表示式也停止運算。例如:

char *p;

...

if ((p != 0) && (strlen(p) > 10)) ...

不用擔心當p為空時strlen無法正確執行,因為如果p不等於0的測試失敗,strlen不會被呼叫。同樣:

int rangecheck(int index)

如果index小於lowerbound,它不會與upperbound進行比較。

c和c++的程式設計師都知道該特性。而且他們也依賴於短路求值法來寫程式。例如在上述第乙個**中,當p為空指標時確保strlen不會被呼叫是很重要的,因為c++標準說(正如c標準所說)用空指標呼叫strlen,結果不確定。

c++允許根據使用者定義的型別,來定製&&和||操作符。方法是過載函式operator&& 和operator||,能在全域性或每個類裡過載。然而如果想使用這種方法,必須知道著正在極大地改變遊戲規則。因為我們以函式呼叫法替代了短路求值法。也就是說如果我們過載了操作符&&,對於我們來說**是這樣的:

if (expression1 && expression2) ...

對於編譯器來說,等同於下面**之一:

if (expression1.operator&&(expression2)) ...

// when operator&& is a member function

if (operator&&(expression1, expression2)) ...

// when operator&& is a global function

這好像沒有什麼不同,但是函式呼叫法與短路求值法是絕對不同的。首先當函式被呼叫時,需要運算其所有引數,所以呼叫函式functions operator&& 和 operator||時,兩個引數都需要計算,換言之,沒有採用短路計算法。第二是c++語言規範沒有定義函式引數的計算順序,所以沒有辦法知道表示式1與表示式2哪乙個先計算。完全可能與具有從左引數到右引數計算順序的短路計算法相反。

因此如果過載&&或||,就沒有辦法提供給程式設計師所期望和使用的行為特性,所以不要過載&&和||。

同樣的理由也適用於逗號操作符。逗號操作符用於組成表示式,經常在for迴圈的更新部分(update part)裡遇見它。例如下面的函式:

// reverse string s in place

void reverse(char s)

}

在for迴圈的最後乙個部分裡,i被增加同時j被減少。在這裡使用逗號很方便,因為在最後乙個部分裡只能使用乙個表示式,分開表示式來改變i和j的值是不合法的。

對於內建型別&&和||,c++有一些規則來定義它們如何運算。與此相同,也有規則來定義逗號操作符的計算方法。乙個包含逗號的表示式首先計算逗號左邊的表示式,然後計算逗號右邊的表示式;整個表示式的結果是逗號右邊表示式的值。所以在上述迴圈的最後部分裡,編譯器首先計算++i,然後是—j,逗號表示式的結果是--j。

如果想寫自己的逗號操作符函式。不幸的是無法模仿。

如果寫乙個非成員函式operator,不能保證左邊的表示式先於右邊的表示式計算,因為函式(operator)呼叫時兩個表示式做為引數被傳遞出去。但是不能控制函式引數的計算順序。所以非成員函式的方法絕對不行。

剩下的只有寫成員函式operator的可能性了。即使這樣也不能依靠於逗號左邊表示式先被計算的行為特性,因為編譯器不一定必須按此方法去計算。因此不能過載逗號操作符,保證它的行為特性與其被料想的一樣。過載它是完全輕率的行為。

下面顯示的符號,它們存在一些限制,也不能過載下面的操作符:

.           .*              ::             ?:

new          delete        sizeof      typeid

static_cast dynamic_cast const_cast reinterpret_cast

可以過載的操作符:

operator new        operator delete

operator   new    operator delete

+    -   *   /   %   ^     &   |     ~

!    =   <   > +=   -=   *=   /=   %=

^= &= |= << >>   >>= <<= ==   !=

<= >= && || ++   --    ,   ->* ->

()

當然能過載這些操作符不是去過載的理由。操作符過載的目的是使程式更容易閱讀,書寫和理解,而不是去迷惑其他人。如果沒有乙個好理由過載操作符,就不要過載。在遇到&&, ||, 和 ,時,找到乙個好理由是困難的,因為無論怎麼努力,也不能讓它們的行為特性與所期望的一樣。

操作符過載

ifndef vertex h define vertex h class vertex vertex float px float py float pz vertex operator const vertex p vertex operator const vertex p void oper...

操作符過載

1.操作符是靜態方法,返回值表示操作結果,引數是運算元。2.操作符過載需要在過載的操作符前加上operator關鍵字。3.最好少用操作符過載,只有在意義明晰而且與內建類的操作一致時才適合使用,以免造成混亂。以建立的分數類 fraction 中的 為例,該分數類中有兩個int型的私有屬性 分子 num...

過載操作符

1.過載操作符1.1 限制過載操作符具有以下限制 1 只有c 預定義的操作符集中的操作符才可以被過載 2 對於內建型別的操作符,它的預定義不能被改變,應不能為內建型別過載操作符,如,不能改變int型的操作符 的含義 3 也不能為內建的資料型別定義其它的操作符 4 只能過載類型別或列舉型別的操作符 5...