最美情侣中文字幕电影,在线麻豆精品传媒,在线网站高清黄,久久黄色视频

歡迎光臨散文網(wǎng) 會(huì)員登陸 & 注冊(cè)

Effective C++ 第二十一條 Don’t try to return a reference when you mus

2023-01-21 20:48 作者:九思519  | 我要投稿

必須返回對(duì)象時(shí),別妄想返回其 reference?

????????學(xué)習(xí)了前面的章節(jié)之后,我們明白了 pass-by-value 和 pass-by-reference 的區(qū)別之后,我們往往會(huì)想優(yōu)化自己的代碼,把原先自己會(huì)寫(xiě) ?pass-by-value 的地方全都替換為 pass-by-reference ,但是如果你對(duì) stack 和 heap 的理解不夠的話(huà),盲目的使用 ?pass-by-reference 會(huì)造成巨大的錯(cuò)誤。下面是一張 X86-64 下 Linux 機(jī)器的虛擬空間圖(來(lái)自 CSAPP 9.72)

????????User stack 由高地址向低地址增大,Run-time heap 由低地址像高地址增長(zhǎng),C++ 中的 new 和 delete 操作底層實(shí)際也是調(diào)用了 malloc 和 free 函數(shù)。函數(shù)中沒(méi)用 malloc、new 創(chuàng)建的對(duì)象都是臨時(shí)對(duì)象(局部變量),存放在 stack 中,由操作系統(tǒng)管理,用 malloc、new 創(chuàng)建的對(duì)象存放在 heap 中,由程序員自己手動(dòng)管理,依靠 C++ 類(lèi)的析構(gòu)函數(shù)也被認(rèn)為是程序員管理。

下面給出一個(gè) case 1

第二十章總結(jié)過(guò),傳參數(shù)為 內(nèi)置類(lèi)型、STL 迭代器、函數(shù)對(duì)象 的時(shí)候,pass-by-value 比 pass-by-reference ,本例子不是為了討論誰(shuí)更高效,是為了說(shuō)明兩個(gè)情況是否程序能夠正常運(yùn)行。

????????case 1 中 pass-by-value 能夠正確運(yùn)行,但是 pass-by-reference 就不行,因?yàn)?fun2 在執(zhí)行 return 之前,會(huì)先計(jì)算 a*b 并存為一個(gè)臨時(shí)變量 temp,返回臨時(shí)變量(return temp)。這個(gè) temp 就是存儲(chǔ)在 stack 中的(沒(méi)有用 new、malloc 創(chuàng)建),由操作系統(tǒng)管理,所以在 fun2 結(jié)束之后,temp 的空間就被釋放了(棧指針 %rsp 移動(dòng)了,但是原先的內(nèi)容沒(méi)有銷(xiāo)毀)。而 fun2 是返回索引,也就是依靠地址尋址,這個(gè)地址又被釋放了,所以程序會(huì)出錯(cuò)。

????????如上圖所示,fun2 結(jié)束之后,返回的是 temp 所在的地址 0x100 ,但是 %rsp 已經(jīng)退回, temp 的空間已經(jīng)釋放,如果有其他臨時(shí)變量產(chǎn)生,0x100 這個(gè)地址的內(nèi)存就會(huì)被覆蓋,導(dǎo)致程序進(jìn)入不可知狀態(tài)。

下面是 case 2

case 2 不會(huì)運(yùn)行出錯(cuò),但是會(huì)造成內(nèi)存泄漏,因?yàn)闆](méi)有代碼來(lái) delete tmp;,如果把這個(gè)任務(wù)丟給客戶(hù)顯然不合適,這就給了客戶(hù)犯錯(cuò)誤的機(jī)會(huì)。

下面使用 static 的方式給出 case 3

使用 static 變量可以既可以使用 pass-by-reference 也可以解決內(nèi)存管理的問(wèn)題,但是也有其他問(wèn)題

????????這段代碼執(zhí)行之后會(huì)發(fā)現(xiàn),執(zhí)行的其實(shí)是 choice 1,這不難理解,因?yàn)?fun2 是返回引用,fun2(1,1)和 fun2(2,2)返回的地址實(shí)際上是同一個(gè)地址,執(zhí)行 if 判斷之前要先執(zhí)行 fun2(1,1) 和 fun2(2,2),fun2(1,1) 會(huì)將 tmp 賦值為 1,再執(zhí)行 fun2(2,2) 會(huì)把 tmp 賦值為 4,再執(zhí)行 if 判斷的時(shí)候?qū)嶋H上執(zhí)行的是 if (4 == 4)…。自然只能是相當(dāng),然后執(zhí)行 choice 1 的代碼。也會(huì)有人想聲明一個(gè) static 數(shù)組專(zhuān)門(mén)來(lái)存放計(jì)算的數(shù)據(jù),但是這個(gè)數(shù)組的大小設(shè)置又是難題。

總結(jié):

絕不要返回 pointer 或者 reference 指向一個(gè) local static 對(duì)象,或返回 reference 指向一個(gè) heap-allocated 對(duì)象,或返回 pointer 或 reference 指向一個(gè) local static 對(duì)象而有可能同時(shí)需要多個(gè)這樣的對(duì)象。


Effective C++ 第二十一條 Don’t try to return a reference when you mus的評(píng)論 (共 條)

分享到微博請(qǐng)遵守國(guó)家法律
常德市| 阿巴嘎旗| 大姚县| 永顺县| 玉屏| 永清县| 石首市| 尉氏县| 合肥市| 道孚县| 屏山县| 方城县| 呼玛县| 东阿县| 扎鲁特旗| 大港区| 勐海县| 新余市| 吴桥县| 宝鸡市| 周口市| 济南市| 东光县| 湄潭县| 金华市| 丹凤县| 龙岩市| 刚察县| 资兴市| 黄大仙区| 惠东县| 施甸县| 庄浪县| 罗源县| 甘洛县| 蕉岭县| 鹤庆县| 濮阳市| 浦东新区| 兴海县| 滕州市|