您好,登錄后才能下訂單哦!
這篇文章主要介紹了C++的this指針實(shí)例分析的相關(guān)知識(shí),內(nèi)容詳細(xì)易懂,操作簡(jiǎn)單快捷,具有一定借鑒價(jià)值,相信大家閱讀完這篇C++的this指針實(shí)例分析文章都會(huì)有所收獲,下面我們一起來(lái)看看吧。
this指針是存在與類(lèi)的成員函數(shù)中,指向被調(diào)用函數(shù)所在的類(lèi)實(shí)例的地址。一個(gè)對(duì)象的this指針并不是對(duì)象本身的一部分,不會(huì)影響sizeof(對(duì)象)的結(jié)果。this作用域是在類(lèi)內(nèi)部,當(dāng)在類(lèi)的非靜態(tài)成員函數(shù)中訪(fǎng)問(wèn)類(lèi)的非靜態(tài)成員的時(shí)候,編譯器會(huì)自動(dòng)將對(duì)象本身的地址作為一個(gè)隱含參數(shù)傳遞給函數(shù)。
先直接給出一個(gè)C++Primer里的類(lèi),你可能還不能完全看懂,但是不著急,我們一點(diǎn)點(diǎn)解釋
class Sales_data { std::string isbn() const { return bookNo; } Sales_data& combine(const Sales_data&); double avg_price() const; std::string bookNo; unsigned untis_sold = 0; double revenue = 0.0; }; //Sales_data非成員函數(shù)接口 Sales_data add(const Sales_data, const Sales_data&); std::ostream& print(std::ostream&, const Sales_data&); std::istream& read(std::istream&, const Sales_data&);
類(lèi)的所有成員都必須在類(lèi)內(nèi)部聲明,但是成員函數(shù)體可以定義在外部,比如我們上面寫(xiě)的Sales_data類(lèi),isbn函數(shù)定義在了內(nèi)部,combine和avg_price函數(shù)定義在了外部
定義在類(lèi)內(nèi)部的函數(shù)是隱式的inline函數(shù)
inline函數(shù),即為調(diào)用時(shí)“內(nèi)聯(lián)地”展開(kāi)的函數(shù),也就是就說(shuō):調(diào)用時(shí),并不通過(guò)函數(shù)調(diào)用的機(jī)制,而是通過(guò)將函數(shù)體直接插入調(diào)用處來(lái)實(shí)現(xiàn)的,比如以下調(diào)用
inline const string & cout
”this“的概念#
我們先看isbn函數(shù)
std::string isbn() const { return bookNo; }
它的參數(shù)列表為空,返回一個(gè)string對(duì)象,那它是怎么知道這個(gè)string對(duì)象是來(lái)自哪個(gè)類(lèi)的?
this
先看一個(gè)調(diào)用的例子
total.isbn() 當(dāng)我們調(diào)用成員函數(shù)時(shí),實(shí)際上是在替某個(gè)對(duì)象(這里是total)調(diào)用它,isbn指向Sales_data的成員(bookNo),則它隱式地指向調(diào)用該函數(shù)的對(duì)象的成員
在total.isbn()調(diào)用中,isbn返回bookNo時(shí),實(shí)際上它隱式地返回total.bookNo
成員函數(shù)isbn又通過(guò)一個(gè)名為this的額外的隱式參數(shù)來(lái)訪(fǎng)問(wèn)調(diào)用它的那個(gè)對(duì)象(this其實(shí)就是指向當(dāng)前對(duì)象的指針),當(dāng)我們調(diào)用一個(gè)成員函數(shù)時(shí),用該函數(shù)的對(duì)象地址初始化this,this就會(huì)指向當(dāng)前對(duì)象
例如調(diào)用total.isbn()則編譯器負(fù)責(zé)把total的地址傳遞給isbn的隱式形參this,可以等價(jià)地理解為編譯器將該調(diào)用重寫(xiě)成了以下形式
std::string isbn() const { return this->bookNo }
因?yàn)閠his的目的總是指向”這個(gè)“對(duì)象,所以this是一個(gè)常量指針(這是一個(gè)頂層const,this指針本身就是常量)
isbn() const#
首先你要知道const的基本用法,頂層cosnt和底層const如何區(qū)別,建議先閱讀這篇文章,下面這幾行代碼方便你回憶起頂層cosnt
int i = 0; int* const p1 = &i; //p1本身是常量,頂層const const int ci = 42; //ci本身是常量,頂層const const int* p2 = &ci; //*在const之后,p2是指向常量的指針,底層const const int* const p3 = p2; //先看左邊是頂層,再看右邊是底層,p3是指向常量的常量指針 const int& r = ci; //聲明引用的const都是底層const,r是一個(gè)對(duì)常量的引用
好進(jìn)入正題
先講結(jié)論:”isbn() const里的const的作用是修改隱式this指針的類(lèi)型
首先我們忘掉isbn,默認(rèn)情況下,this的類(lèi)型是指向類(lèi)類(lèi)型的 非常量版本的 常量指針(這是一個(gè)頂層const,this指針自己是常量,但是它所指向的對(duì)象并不是常量),在Sales_data的成員函數(shù)中,this的默認(rèn)類(lèi)型是Sales_data* const
盡管this是隱式的,但也遵循初始化規(guī)則,所以默認(rèn)情況下我們不能把this直接綁定到一個(gè)常量對(duì)象上,同時(shí)也不能在一個(gè)常量對(duì)象上調(diào)用普通的函數(shù)成員(需要用到this)
具體來(lái)說(shuō),如果,我是說(shuō)如果,如果isbn是一個(gè)普通函數(shù)沒(méi)有const,this也是一個(gè)普通的指針,isbn內(nèi)不會(huì)改變this所指的對(duì)象(只是返回bookNo),則我們應(yīng)該把this聲明成const Sales_data* const,所以把this設(shè)置為指向常量的指針可以提高靈活性
然而this隱式的,是不會(huì)出現(xiàn)在參數(shù)列表中的,所以在哪將this聲明稱(chēng)指向常量的指針呢?C++的做法就是允許把const關(guān)鍵字放在成員函數(shù)的參數(shù)列表之后,就是我們看到的isbn() const,此時(shí)緊跟在參數(shù)列表后面的const表示this是一個(gè)指向常量的指針,像這樣使用const的成員函數(shù)常被稱(chēng)作常量成員函數(shù)
//下面代碼是非法的,只用于說(shuō)明隱式的this指針如何使用,但我們不能顯式定義this指針 //謹(jǐn)記此處的this是一個(gè)指向常量的指針,因?yàn)閕sbn是一個(gè)常量成員
std::string Sales_data::isbn(const Sales_data *const this){ return this->isbn; }
定義一個(gè)返回this對(duì)象的函數(shù)#
我們之前在Sales_data內(nèi)聲明了一個(gè)combine函數(shù)
Sales_data& combine(const Sales_data&);
現(xiàn)在我們?cè)谕獠慷x這個(gè)函數(shù)
Sales_data& Sales_data::combine(const Sales_data &rhs){ untis_sold += rhs.untis_sold; revenue += rhs.revenue; return *this; }
Sales_data::combine使用作用域運(yùn)算符以說(shuō)明:我們定義了一個(gè)名為combine的函數(shù),并且該函數(shù)聲明在Sales_data類(lèi)的作用域內(nèi),因此當(dāng)combine使用untis_sold和revenue時(shí),也是隱式地使用了Sales_data的成員
我們調(diào)用這個(gè)combine時(shí)
total.combine(trans)
total的地址被綁定到隱式的this參數(shù)上,而rhs綁定到了trans上
你應(yīng)該注意到了,這個(gè)函數(shù)的關(guān)注點(diǎn)應(yīng)該在于返回類(lèi)型和返回語(yǔ)句
combine設(shè)計(jì)的初衷是盡量模仿+=運(yùn)算符,+=把左側(cè)的運(yùn)算對(duì)象當(dāng)成左值返回,為了盡可能一致,combine必須返回引用類(lèi)型(這時(shí)左側(cè)運(yùn)算對(duì)象是一個(gè)Sales_data對(duì)象,所以返回類(lèi)型為Sales_data&)
怎么返回呢,現(xiàn)在我們就不需要使用隱式的this指針訪(fǎng)問(wèn)函數(shù)調(diào)用者 的某個(gè)具體成員,而是需要把調(diào)用函數(shù)的對(duì)象當(dāng)成一個(gè)整體來(lái)訪(fǎng)問(wèn)
return *this;
return語(yǔ)句解引用this指針,獲得了執(zhí)行該函數(shù)的對(duì)象,total.combine(trans)就會(huì)返回對(duì)total的引用。
關(guān)于“C++的this指針實(shí)例分析”這篇文章的內(nèi)容就介紹到這里,感謝各位的閱讀!相信大家對(duì)“C++的this指針實(shí)例分析”知識(shí)都有一定的了解,大家如果還想學(xué)習(xí)更多知識(shí),歡迎關(guān)注億速云行業(yè)資訊頻道。
免責(zé)聲明:本站發(fā)布的內(nèi)容(圖片、視頻和文字)以原創(chuàng)、轉(zhuǎn)載和分享為主,文章觀(guān)點(diǎn)不代表本網(wǎng)站立場(chǎng),如果涉及侵權(quán)請(qǐng)聯(lián)系站長(zhǎng)郵箱:is@yisu.com進(jìn)行舉報(bào),并提供相關(guān)證據(jù),一經(jīng)查實(shí),將立刻刪除涉嫌侵權(quán)內(nèi)容。