背景
C++中提供了很多操作符且定義了什么時(shí)候可以用于操作基本類型,其還允許我們定義用于操作class類型的操作符,接下來幾篇文章將會(huì)介紹C++中用于基本類型的操作符,與此同時(shí)也會(huì)介紹一些庫中操作符。一個(gè)表達(dá)式是由一個(gè)或多個(gè)操作符組成的并且返回一個(gè)結(jié)果。一個(gè)最簡(jiǎn)單的表達(dá)式就是一個(gè)變量或者字面量,更加復(fù)雜的表達(dá)式是由一個(gè)操作符和一個(gè)或多個(gè)操作數(shù)組成。
基礎(chǔ)知識(shí)
C++中有一些影響表達(dá)式計(jì)算的基礎(chǔ)概念,所以我們?cè)谑褂们靶枰攘私庖幌逻@些基本概念。
基本概念
C++中有一元運(yùn)算符也有二元運(yùn)算符,一元運(yùn)算符就像是地址操作符&或者是解引用操作符,都是作用于一個(gè)操作數(shù)。類似==就是二元操作符,是作用在兩個(gè)操作數(shù)上的。還有一個(gè)三元運(yùn)算符,其可以操作三個(gè)操作數(shù),函數(shù)調(diào)用則不限制操作數(shù)的數(shù)量。其中像即可以是一元運(yùn)算符(解引用符),也可以是二元運(yùn)算符(乘法符號(hào)),在實(shí)際使用中由其所處的上下文環(huán)境決定。
理解這么多運(yùn)算符需要理解運(yùn)算符的優(yōu)先級(jí)和結(jié)合性,這取決于操作數(shù)的運(yùn)算順序,以下就是一個(gè)例子,*操作符的操作數(shù)可以是10和20,也可以是是10和20/2,或者是15和20/2,該如何理解這個(gè)表達(dá)式呢,接下來我們?cè)敿?xì)說明。
操作數(shù)轉(zhuǎn)換
作為計(jì)算表達(dá)式的一部分,操作數(shù)會(huì)經(jīng)常從一個(gè)類型轉(zhuǎn)換為另一個(gè)類型,例如二元運(yùn)算符通常希望兩個(gè)操作數(shù)是同一個(gè)類型,這些運(yùn)算符可以用于不同類型的操作數(shù)只要兩個(gè)操作可以轉(zhuǎn)化為同一個(gè)類型。例如我們可以將一個(gè)整型轉(zhuǎn)化成一個(gè)浮點(diǎn)型,但是我們無法將一個(gè)指針類型轉(zhuǎn)化為一個(gè)浮點(diǎn)型。
運(yùn)算符重載
C++定義了應(yīng)用于基本類型和復(fù)合類型的操作符含義,我們自己可以定義操作符作用于class類型時(shí)操作符的含義,這種定義給了已有操作符的其他含義,這種我們稱之為運(yùn)算符重載。IO庫中的<<和>>操作符就是重載遠(yuǎn)算符。
當(dāng)我們使用重載運(yùn)算符時(shí),運(yùn)算符的含義。操作數(shù)和最后的結(jié)果都取決于運(yùn)算符是如何定義的,但是操作數(shù)的數(shù)量和優(yōu)先級(jí)和結(jié)合性是不會(huì)改變的。
左值和右值
C++中的表達(dá)式不是左值(rvalue)就是右值(rvalue),這個(gè)名稱是從C中繼承過來的,其是為了好記憶,左值可以在賦值的左邊,右值則不可以。在C++中左值和右值更好區(qū)分,一個(gè)左值表達(dá)式代表一個(gè)對(duì)象或者一個(gè)函數(shù),然而需要注意的是一些左值表達(dá)式如const對(duì)象不能作為賦值操作符的左操作數(shù)。而且一些表達(dá)式產(chǎn)生對(duì)象但是是返回右值而不是返回左值??偟膩碚f,當(dāng)我將一個(gè)對(duì)象當(dāng)作右值使用時(shí)返回的他的值,當(dāng)作左值使用時(shí)返回的是其地址。
操作符在需要左值或者右值以及返回左值或者右值時(shí)是不同的,我們可以將一個(gè)左值當(dāng)作右值使用,但是卻不能將右值當(dāng)作左值使用。
當(dāng)使用decltype時(shí)左值和右值也不同,當(dāng)我對(duì)一個(gè)表達(dá)式使用decltype,如果表達(dá)式返回的是左值,函數(shù)返回則是引用,例如如果p 是int 類型,decltype(p)返回的時(shí)int&,如果運(yùn)算表達(dá)式是右值如地址操作符如decltype(&p)返回int , 這是一個(gè)指針,指向一個(gè)指向int類型的指針。
優(yōu)先級(jí)和結(jié)合性
一個(gè)表達(dá)式包含兩或兩個(gè)個(gè)以上的操作符的表達(dá)式是復(fù)合表達(dá)式,計(jì)算一個(gè)復(fù)合表達(dá)式需要將利用操作符將操作數(shù)分組,優(yōu)先級(jí)和結(jié)合性決定如何分組,開發(fā)者也可以通過括號(hào)來強(qiáng)制分組。
通常表達(dá)式的值依賴于子表達(dá)式如何分組,操作數(shù)將會(huì)和優(yōu)先級(jí)高的操作符結(jié)合在一起,例如乘和除的優(yōu)先級(jí)相同,但是他們的優(yōu)先級(jí)比加高,所以要先算乘除,后算加減。在優(yōu)先級(jí)的相同的情況下由結(jié)合性決定如何分組,算術(shù)操作符是向左結(jié)合,這意味著在優(yōu)先級(jí)相同的情況下從左向右分組:
- 因?yàn)閮?yōu)先級(jí)所以3 + 4 * 5結(jié)果是23而不是35
- 因?yàn)榻Y(jié)合性所以20 - 15 - 3是2而不是8
運(yùn)算順序
優(yōu)先級(jí)決定了操作數(shù)如何被分組,但是其并未確定哪一個(gè)操作數(shù)先被運(yùn)算,在絕大多數(shù)情況下這個(gè)順序是不固定的,例如在下面的例子中,我們知道f1和f2必須要在乘法執(zhí)行前調(diào)用,然后將他們的結(jié)果相乘,但是我們并不知道f1和f2哪個(gè)先調(diào)用:
int i = f1() * f2();
對(duì)于沒有指定運(yùn)算順序的操作符而言,一個(gè)表達(dá)式指向并改變同一個(gè)對(duì)象會(huì)發(fā)生錯(cuò)誤,這么做的表達(dá)式會(huì)引發(fā)未定義的錯(cuò)誤。一個(gè)簡(jiǎn)單的例子,<< 操作符并不指定操作數(shù)的運(yùn)算順序,其結(jié)果就是輸出表達(dá)式未知。
int i = 0;
std::cout<
有四個(gè)運(yùn)算符是保證操作數(shù)的遠(yuǎn)算順序,&&操作符先運(yùn)算左邊,只有左邊為true才會(huì)運(yùn)算右邊,|| , ?:和,也會(huì)確定操作順序。
成員獲取操作符
點(diǎn)操作符.和箭頭操作符->都能獲取到成員,點(diǎn)操作符可以獲取到class類型的成員,而箭頭操作符可以獲取到指針的成員:
string s1 = "a string", *p = &s1;
auto n = s1.size();
n = (*p).size();
n = p->size(); //等價(jià)于(*p).size()
?由于解引用符有優(yōu)先級(jí)低于點(diǎn)操作符,所以我們需要使用括號(hào)改變遠(yuǎn)算順序
?
條件操作符
條件操作符能夠簡(jiǎn)化if-else的邏輯結(jié)構(gòu),通常的使用形式如下
cond?expr1 : expr2;
其中cond是一個(gè)條件,如果cond為true,運(yùn)算expr1,反之則運(yùn)算expr2,例子如下
string finalgrade = (grade < 60)? "failed" : "pass";
條件操作符也可以嵌套:
finalgrade = (grade > 90) ? "high pass": (grade < 60) ? "fail" : "pass";
-
C++
+關(guān)注
關(guān)注
22文章
2108瀏覽量
73651 -
Class
+關(guān)注
關(guān)注
0文章
53瀏覽量
19733 -
操作符
+關(guān)注
關(guān)注
0文章
21瀏覽量
9042
發(fā)布評(píng)論請(qǐng)先 登錄
相關(guān)推薦
評(píng)論