c++ - 实际获得的动态分配内存的大小怎么确定
怪我咯
怪我咯 2017-04-17 14:20:17
0
5
672
怪我咯
怪我咯

走同样的路,发现不同的人生

全部回覆(5)
伊谢尔伦

知乎上我有看過:

我先問你個問題:指標中是沒有所在記憶體區塊大小的資訊的,那麼 free 怎麼才能知道要釋放的記憶體區塊有多大呢?於是,對於大多數記憶體分配器,malloc 申請的實際記憶體比你要求的空間大幾個字節,裡面儲存了額外的資料來記錄這塊記憶體有多大,一般就是直接存在指標左邊。 free 的時候,就會去讀取指標位址減去一個常數之後的那塊內存,來取得記憶體區塊的資訊。因此如果你 free 一個不指向記憶體區塊開始處的指針,free 的時候就會把其他的資料錯誤解釋成記憶體區塊的信息,(大機率)導致程式崩潰。當然現代的記憶體分配器對於不同大小的記憶體申請,會採用不同的分配策略,但無論策略如何,去 free 一個不是 malloc 來的指針,都是非常危險的舉動。

見:https://www.zhihu.com/questio...

黄舟

實際分配的記憶體比請求的多多少標準中並沒有規定,依賴於malloc的實現,這屬於開發者不必關心的實現。

小葫芦

決定實際分配記憶體的大小

沒有萬能的辦法。因為這屬於記憶體分配器的實作細節。你要知道,你得去看你所使用的記憶體分配器是怎麼分配記憶體的。

大家讲道理

CSAPP中有講到這部分,不僅會多出記錄大小的頭,還會因為進行對齊操作而獲得比申請更多的內存

左手右手慢动作

作業系統是需要知道每個指標分配了多少記憶體的,我們在呼叫delete的時候也沒有告訴作業系統這個指標只想的區域佔用了多少內存,所以肯定有一個地方保存著這個值,而這個值在不同的作業系統有不同的實現,例如最簡單的一種實現就是在每個指標前面一個位元組用來保存記憶體分配的長度,一般作業系統都會提供一個函數來取得這個實際記憶體的大小,例如malloc_size之類的函數。
如果有興趣可以看看redis源碼,zmalloc.h和zmalloc.c
https://github.com/antirez/re...

#if defined(USE_TCMALLOC)
#define ZMALLOC_LIB ("tcmalloc-" __xstr(TC_VERSION_MAJOR) "." __xstr(TC_VERSION_MINOR))
#include <google/tcmalloc.h>
#if (TC_VERSION_MAJOR == 1 && TC_VERSION_MINOR >= 6) || (TC_VERSION_MAJOR > 1)
#define HAVE_MALLOC_SIZE 1
#define zmalloc_size(p) tc_malloc_size(p)
#else
#error "Newer version of tcmalloc required"
#endif

#elif defined(USE_JEMALLOC)
#define ZMALLOC_LIB ("jemalloc-" __xstr(JEMALLOC_VERSION_MAJOR) "." __xstr(JEMALLOC_VERSION_MINOR) "." __xstr(JEMALLOC_VERSION_BUGFIX))
#include <jemalloc/jemalloc.h>
#if (JEMALLOC_VERSION_MAJOR == 2 && JEMALLOC_VERSION_MINOR >= 1) || (JEMALLOC_VERSION_MAJOR > 2)
#define HAVE_MALLOC_SIZE 1
#define zmalloc_size(p) je_malloc_usable_size(p)
#else
#error "Newer version of jemalloc required"
#endif

#elif defined(__APPLE__)
#include <malloc/malloc.h>
#define HAVE_MALLOC_SIZE 1
#define zmalloc_size(p) malloc_size(p)
#endif

也可以了解 tcmalloc 和 jemalloc 的實作

熱門教學
更多>
最新下載
更多>
網站特效
網站源碼
網站素材
前端模板