日韩在线免费播放-日韩在线免费av-日韩在线免费-日韩在线毛片-国产高清不卡视频-国产高清不卡

當前位置:首頁 > 嵌入式培訓(xùn) > 嵌入式學(xué)習(xí) > 講師博文 > C++中placement new和delete討論

C++中placement new和delete討論 時間:2018-09-27      來源:未知

在程序設(shè)計中頻繁地進行動態(tài)內(nèi)存分配和釋放容易造成內(nèi)存碎片,給需要長期穩(wěn)定運行的系統(tǒng)帶來了隱患。盡管現(xiàn)代操作系統(tǒng)在內(nèi)存管理的穩(wěn)健性上已經(jīng)有了較大提高,但是動態(tài)內(nèi)存分配的效率、穩(wěn)定性等問題仍然是一個困擾。所以在需要長期穩(wěn)定運行的、生命攸關(guān)的嵌入式設(shè)備程序開發(fā)中通常都要避免過多地使用new和delete,甚至禁止使用C++的標準庫,因為其中經(jīng)常進行動態(tài)內(nèi)存的分配與釋放。然而要充分享用使用C++帶來的便利之處,動態(tài)地創(chuàng)建和銷毀對象的能力還是非常有必要的。

本文引用地址://www.bsfkj.cn/emb/Column/7365.html

通常的new運算符會在堆中動態(tài)分配內(nèi)存,并在成功分配的內(nèi)存空間上調(diào)用相應(yīng)對象的構(gòu)造函數(shù),而delete運算符會先在該內(nèi)存空間上調(diào)用相應(yīng)對象的析構(gòu)函數(shù),然后釋放該內(nèi)存空間。然而在C++中,可以通過對new和delete的重載來實現(xiàn)特殊的功能。不過在程序員編寫的new和delete的重載函數(shù)中都只是負責(zé)內(nèi)存空間的分配和釋放,編譯器會在new時強制調(diào)用構(gòu)造函數(shù),在delete時強制調(diào)用析構(gòu)函數(shù)。因為在C++中初始化和清除工作是強制進行的,用戶無權(quán)選擇避開構(gòu)造函數(shù)和析構(gòu)函數(shù)的調(diào)用。

要想在這些特殊的情況下能實現(xiàn)對象的創(chuàng)建和銷毀,C++中提供了placement new來應(yīng)對。在C++中因為可以對運算符進行重載,所以只需對operator new()進行placement重載就能實現(xiàn)在事先分配好的內(nèi)存空間上調(diào)用構(gòu)造函數(shù)來動態(tài)創(chuàng)建對象,通過不太常用的對析構(gòu)函數(shù)的顯式調(diào)用來銷毀對象。在這種情況下不涉及內(nèi)存空間的分配和釋放,從而不會導(dǎo)致動態(tài)的存儲管理,不會對系統(tǒng)的長期穩(wěn)定運行帶來影響。

在C++中placement new運算符是通過對new運算符的重載來實現(xiàn)的,它在嵌入式開發(fā)中有著重要的用途。因為我們經(jīng)常想在內(nèi)存的某個指定位置上放置一個對象(在嵌入式底層開發(fā)中,一個對象可能和一個特定的硬件是直接相關(guān)的)。

Placement new的主要用途就是:反復(fù)使用一塊較大的分配成功的內(nèi)存來構(gòu)造不同類型的對象或者它們的數(shù)組。比如,可以先申請一個足夠大的字符數(shù)組,然后當需要時在它上面構(gòu)造不同類型的對象或其數(shù)組。

定位new運算符的基本語法為

char a[100];

X* xp = new(a) X;

其中X是某個事先定義好類,a是一塊尺寸大于等于sizeof(X)的內(nèi)存區(qū)域的首地址。由于內(nèi)存區(qū)域是事先已經(jīng)存在的,placement僅僅只是在相應(yīng)的內(nèi)存空間上調(diào)用X的構(gòu)造函數(shù)來初始化該片內(nèi)存區(qū)域。

下面的例子顯示了如何在一個特定的內(nèi)存單元里放置一個對象。

#include

using namespace std;

class X {

int i;

public:

X(int ii = 0) : i(ii) {

cout << "this = " << this << endl;

}

~X() {

cout << "X::~X(): " << this << endl;

}

void* operator new(size_t, void* loc) {

return loc;

}

};

int main()

{

int l[10];

cout << "l = " << l << endl;

X* xp = new(l) X(47);

xp->X::~X();

return 0;

}

從中可以看到數(shù)組l的地址和構(gòu)造以及析構(gòu)函數(shù)中輸出的this指針的值是相同的。

注意operator new()僅僅返回了傳遞給它的指針,因此調(diào)用者可以決定將對象存放在哪里,這時在該指針所指向的那塊內(nèi)存上,作new表達式一部分的構(gòu)造函數(shù)將被調(diào)用。概括來說就是內(nèi)存空間是事先分配好的,placement new只是在其上調(diào)用構(gòu)造函數(shù)來動態(tài)創(chuàng)建對象。

然而在銷毀對象時則需要格外小心,因為空間不是由new創(chuàng)建的,所以在銷毀對象時也應(yīng)該將對象的析構(gòu)和內(nèi)存空間的釋放分開來做。我們要銷毀對象就需要調(diào)用析構(gòu)函數(shù),但此時不能將內(nèi)存空間釋放掉,因為內(nèi)存空間不是由new所分配出來的。解決辦法是用非常特殊的語法,我們可以顯式的調(diào)用構(gòu)造函數(shù)。例如:

xp->X::~X();

這樣將會只銷毀對象而不會釋放內(nèi)存。通過placement new和顯式調(diào)用析構(gòu)函數(shù)的方式我們就可以在已有的空間上動態(tài)地創(chuàng)建和銷毀對象。在嵌入式領(lǐng)域,為了穩(wěn)定性,我們可以在程序一開始時分配好足夠的空間,在上面構(gòu)造和銷毀對象,充分享受這種便利性,同時也避免了通常的new和delete所帶來的內(nèi)存碎片問題。

使用placement new構(gòu)造起來的對象或其數(shù)組,要顯示地調(diào)用它們的析構(gòu)函數(shù)來銷毀(析構(gòu)函數(shù)并不釋放對象的內(nèi)存),千萬不要使用delete。這是因為,placement new構(gòu)造起來的對象或其數(shù)組的大小并不一定等于原來分配的內(nèi)存大小,而且空間也不一定是在堆上分配的,使用delete的話將會出現(xiàn)嚴重的問題。

上一篇:NFC之PN532使用

下一篇:container_of分析

熱點文章推薦
華清學(xué)員就業(yè)榜單
高薪學(xué)員經(jīng)驗分享
熱點新聞推薦
前臺專線:010-82525158 企業(yè)培訓(xùn)洽談專線:010-82525379 院校合作洽談專線:010-82525379 Copyright © 2004-2022 北京華清遠見科技集團有限公司 版權(quán)所有 ,京ICP備16055225號-5,京公海網(wǎng)安備11010802025203號

回到頂部

主站蜘蛛池模板: 欧美黑人巨大精品videos| 白鹭的简介资料| 市川美织| 电影《真爱》完整播放| 江南好简谱| 开心日记| 看香谱二十四法图解| 孤岛惊魂| 李坤忆| 胡晶| 洗鼻器的使用方法教程| free hd xxxx moms movie777| 鲜于善| 科室对分级护理落实情况检查记录 | 洛嘉| 奇骏车友会| 性欧美女同| 女王的条件| 男女男在线观看| 苦菜花电视剧| 阮虔芷个人资料| 萱草花合唱谱二声部| 手机在线观看电影网| 花宵道中1| 局内人电影完整版| 孽子 电影| 漂亮主妇| 拔萝卜电影| 潇洒走一回广场舞完整版| 郑艳丽曹查理主演的影片| 田教授的28个保姆演员表| 公民的基本权利和义务教学设计| 给我| 全能住宅改造王| 高手论坛| 被抛弃的青春1982| 男插女曲| 电影《很差劲》在线观看| 搜狐手机网首页新闻| 汪汪队100集全免费| 莫斯科保卫战电影|