在线观看www成人影院-在线观看www日本免费网站-在线观看www视频-在线观看操-欧美18在线-欧美1级

0
  • 聊天消息
  • 系統消息
  • 評論與回復
登錄后你可以
  • 下載海量資料
  • 學習在線課程
  • 觀看技術視頻
  • 寫文章/發帖/加入社區
會員中心
創作中心

完善資料讓更多小伙伴認識你,還能領取20積分哦,立即完善>

3天內不再提示

如何讓new操作符不分配內存,只構造

Linux愛好者 ? 來源:Linux愛好者 ? 作者:Linux愛好者 ? 2021-01-19 17:01 ? 次閱讀

【導讀】:本文主要介紹如何讓new操作符不分配內存,只構造。

問題

c++中的new操作符通常完成兩個工作分配內存及調用相應的構造函數。

請問:

如何讓new操作符不分配內存,只調用構造函數?

這樣的用法有什么用?

placement new的含義

placement new可以實現不分配內存,只調用構造函數。

void*operatornew(size_t,void*p)throw(){returnp;}

placement new的執行忽略了size_t參數,只返還第二個參數。

其結果是允許用戶把一個對象放到一個特定的地方,達到調用構造函數的效果。

用法如下:

#include #include classTest { public: Test() { std::cout<~Test(); } }

輸出:

Constructor Constructor Destructor

和其他普通的new不同的是,它在括號里多了另外一個參數。比如:

Widget*p=newWidget;---------//ordinarynew pi=new(ptr)int;pi=new(ptr)int;//placementnew

括號里的參數ptr是一個指針,它指向一個內存緩沖器,placement new將在這個緩沖器上分配一個對象。

Placement new的返回值是這 個被構造對象的地址(比如括號中的傳遞參數)。

placement new主要適用于:在對時間要求非常高的應用程序中,因為這些程序分配的時間是確定 的;長時間運行而不被打斷的程序;以及執行一個垃圾收集器 (garbage collector)。

new 、operator new 和 placement new 區別

new :不能被重載,其行為總是一致的。它先調用operator new分配內存,然后調用構造函數初始化那段內存。

operator new:要實現不同的內存分配行為,應該重載operator new,而不是new。

delete和operator delete類似。delete首先調用對象的析構函數,然后調用operator delete釋放掉所使用的內存。

placement new:只是operator new重載的一個版本。它并不分配內存,只是返回指向已經分配好的某段內存的一個指針。因此不能刪除它,但需要調用對象的析構函數。

new 操作符的執行過程

調用operator new分配內存 ;

調用構造函數生成類對象;

返回相應指針。

placement new允許你在一個已經分配好的內存中(棧或者堆中)構造一個新的對象。原型中void*p實際上就是指向一個已經分配 好的內存緩沖區的的首地址。

Placement new 存在的理由

用Placement new 解決buffer的問題

問題描述:

用new分配的數組緩沖時,由于調用了默認構造函數,因此執行效率上不佳。若沒有默認構造函數則會發生編譯時錯誤。如果你想在預分配的內存上創建對象,用缺省的new操作符是行不通的。要解決這個問題,你可以用placement new構造。它允許你構造一個新對象到預分配的內存上。

增大時空效率的問題

使用new操作符分配內存需要在堆中查找足夠大的剩余空間,顯然這個操作速度是很慢的,而且有可能出現無法分配內存的異常(空間不夠)。

placement new 就可以解決這個問題。我們構造對象都是在一個預先準備好了的內存緩沖區中進行,不需要查找內存,內存分配的時間是常數;而且不會出現在程序運行中途出現內 存不足的異常。所以,placement new非常適合那些對時間要求比較高,長時間運行不希望被打斷的應用程序。

使用步驟

在很多情況下,placement new的使用方法和其他普通的new有所不同。這里提供了它的使用步驟。

第一步 緩存提前分配

有三種方式:

為了保證通過placement new使用的緩存區的memory alignmen(內存隊列)正確準備,使用普通的new來分配它:在堆上進行分配

classTask; char*buff=new[sizeof(Task)];//分配內存

(請注意auto或者static內存并非都正確地為每一個對象類型排列,所以,你將不能以placement new使用它們。)

在棧上進行分配

classTask; charbuf[N*sizeof(Task)];//分配內存

還有一種方式,就是直接通過地址來使用。(必須是有意義的地址)

void*buf=reinterpret_cast(0xF00F);

第二步:對象的分配

在剛才已分配的緩存區調用placement new來構造一個對象。

Task*ptask=new(buf)Task

第三步:使用

按照普通方式使用分配的對象:

ptask->memberfunction(); ptask->member; //...

第四步:對象的析構

一旦你使用完這個對象,你必須調用它的析構函數來毀滅它。按照下面的方式調用析構函數:

ptask->~Task();//調用外在的析構函數

第五步:釋放

你可以反復利用緩存并給它分配一個新的對象(重復步驟2,3,4)如果你不打算再次使用這個緩存,你可以象這樣釋放它:

delete[]buf;

跳過任何步驟就可能導致運行時間的崩潰,內存泄露,以及其它的意想不到的情況。如果你確實需要使用placement new,請認真遵循以上的步驟。

性能對比

采用placement new和new的方式創建和刪除對象一萬次,統計時間,單位是us。

intmain() { { uint64_tstart=GetCurrentTimeInMicroSeconds(); for(uint32_ti=0;i~Test(); } std::cout<

結果:

placementnew:186 new:1448

結論:在頻繁構造和析構對象的場景中,placement new對性能有7倍的提升。

責任編輯:lq

聲明:本文內容及配圖由入駐作者撰寫或者入駐合作網站授權轉載。文章觀點僅代表作者本人,不代表電子發燒友網立場。文章及其配圖僅供工程師學習之用,如有內容侵權或者其他違規問題,請聯系本站處理。 舉報投訴
  • 緩沖器
    +關注

    關注

    6

    文章

    1923

    瀏覽量

    45533
  • 函數
    +關注

    關注

    3

    文章

    4338

    瀏覽量

    62749
  • 應用程序
    +關注

    關注

    37

    文章

    3283

    瀏覽量

    57753

原文標題:如何讓 new 操作符只構造,不申請內存

文章出處:【微信號:LinuxHub,微信公眾號:Linux愛好者】歡迎添加關注!文章轉載請注明出處。

收藏 人收藏

    評論

    相關推薦

    邏輯異或運算在Python中的用法

    在Python編程語言中,邏輯異或運算并不直接作為一個內置的操作符存在,因為Python更側重于高級編程和可讀性,并沒有直接提供異或運算的簡寫形式用于邏輯運算(真/假值的異或)。然而
    的頭像 發表于 11-19 09:46 ?229次閱讀

    技術干貨驛站 ▏解鎖C語言高效編程秘訣:深入解析運算與優先級

    和邏輯表達。1位運算“程序中的所有數在計算機內存中都是以二進制的形式儲存的,位運算可以直接對整數在內存中的二進制位進行操作,運位算包括位邏輯運算和移位運算。變量A
    的頭像 發表于 10-13 08:09 ?296次閱讀
    技術干貨驛站 ▏解鎖C語言高效編程秘訣:深入解析運算<b class='flag-5'>符</b>與優先級

    鴻蒙原生應用元服務開發-倉頡基礎數據類型整數類型

    (十進制)。 整數類型支持的操作 整數類型默認支持的操作符包括:算術操作符、位操作符、關系操作符、自增和自減
    發表于 09-13 14:55

    鴻蒙原生應用元服務開發-倉頡基礎數據類型布爾類型

    let b: Bool = false 布爾類型支持的操作 布爾類型支持的操作符包括:邏輯操作符(邏輯非!,邏輯與 &&,邏輯或 ||)、部分關系操作符
    發表于 09-09 09:57

    轉載 golang內存分配

    . 線程擁有一定的 cache, 可用于無鎖分配. 同時 Go 對于 GC 后回收的內存頁, 并不是馬上歸還給操作系統, 而是會延遲歸還, 用于滿足未來的內存需求. ?? ? 在 1.
    的頭像 發表于 09-05 14:12 ?280次閱讀
    轉載 golang<b class='flag-5'>內存</b><b class='flag-5'>分配</b>

    c語言中從左到右結合怎么看

    在C語言中,操作符的結合性(Associativity)是指當操作符在表達式中連續出現時,它們如何與操作數結合的順序。對于大多數二元操作符(即需要兩個
    的頭像 發表于 08-20 11:42 ?970次閱讀

    HarmonyOS Next原生應用開發-從TS到ArkTS的適配規則(八)

    :arkts-no-props-by-index 級別:錯誤 ArkTS不支持動態聲明字段,不支持動態訪問字段。只能訪問已在類中聲明或者繼承可見的字段,訪問其他字段將會造成編譯時錯誤。 使用點操作符訪問字段,例如
    發表于 07-23 16:54

    可以用os_malloc() 分配多少內存?有哪些限制?

    我可以用 os_malloc() 分配多少內存?有哪些限制?
    發表于 07-15 06:32

    FPGA學習筆記---基本語法

    3、信號類型:wire, reg, tri等 4、參數定義:parameter 5、運算操作符:各種邏輯操作符、移位操作符、算數操作符等 6、比較判斷:if ... else, ca
    發表于 06-23 14:58

    ESP32 IDF 4.3創建任務使用外部PSRAM分配內存,在任務里操作FLASH死機的原因?

    ESP32 IDF 4.3 創建任務使用外部PSRAM分配內存,在任務里操作FLASH一定會死機,請問是什么原因或者有這種限制嗎 static StaticTask_t xTaskBuffer
    發表于 06-19 06:10

    ESP32S3+LVGL創建一個界面,請問能在SPIRAM分配內存,IRAM不分配嗎?

    各位前輩好。ESP32S3+LVGL的開發的過程中發現,創建一個界面,會同時在SPIRAM和IRAM分配相同大小的內存。請問能在SPIRAM分配
    發表于 06-06 07:45

    FreeRTOS如何在中斷中調用內存分配函數?

    最近在玩FreeRTOS,遇到一個問題,就是不知如何在中斷中調用內存分配函數。pvPortMalloc函數中會調用xTaskResumeAll,而這個函數不能再中斷調用,所以請問在中斷中進行內存
    發表于 05-08 08:25

    C語言內存泄漏問題原理

    內存泄漏問題只有在使用堆內存的時候才會出現,棧內存不存在內存泄漏問題,因為棧內存會自動分配和釋放
    發表于 03-19 11:38 ?540次閱讀
    C語言<b class='flag-5'>內存</b>泄漏問題原理

    Linux內核內存管理之內核非連續物理內存分配

    我們已經知道,最好將虛擬地址映射到連續頁幀,從而更好地利用緩存并實現更低的平均內存訪問時間。然而,如果對內存區域的請求并不頻繁,那么考慮基于通過連續線性地址訪問非連續頁幀的分配方案是有意義的。該模式
    的頭像 發表于 02-23 09:44 ?1018次閱讀
    Linux內核<b class='flag-5'>內存</b>管理之內核非連續物理<b class='flag-5'>內存</b><b class='flag-5'>分配</b>

    Linux內核內存管理之ZONE內存分配

    內核中使用ZONE分配器滿足內存分配請求。該分配器必須具有足夠的空閑頁幀,以便滿足各種內存大小請求。
    的頭像 發表于 02-21 09:29 ?918次閱讀
    主站蜘蛛池模板: 成年人三级视频| 亚洲天堂婷婷| 欧美18性欧美丶黑吊| 777影院| 4399一级成人毛片| 欧美操穴视频| 亚洲福利一区| 99热久久精品最新| 四虎精品永久在线网址| 青草91| 狠狠色噜噜狠狠色综合久| 国产国产人免费人成成免视频 | 亚洲一区二区三区电影| 亚洲国产精品久久婷婷| 色丁香在线视频| 精品伊人久久香线蕉| 99精品国产高清自在线看超| 天天操好逼| 福利毛片| 午夜男人视频| 性欧美黑人xxxx| 欧日韩美香蕉在线观看| 韩国三级在线不卡播放| 亚洲在线a| 福利视频自拍偷拍| 久久精品人人爽人人爽快| 泰国一级毛片aaa下面毛多| 男人你懂的网站| freesex性欧美炮机喷潮| 手机看片日韩永久福利盒子| 人人揉揉香蕉大免费不卡| 99久久久久国产精品免费| 色视频网站色视频播放| 黄色视屏日本| 失禁h啪肉尿出来高h健身房| www.免费| 不卡免费在线视频| 日本成人黄色网址| 亚洲第一香蕉视频| 啪啪免费网| 亚洲电影av|