C C 中有關記憶體問題的彙總

2021-09-24 13:06:13 字數 2487 閱讀 6048

型別

32位環境下所佔位元組數

64位環境下所佔位元組數

char11

short int22

int4

4long int48

long long int88

float44

double88

char*44

int *44

特別地,null占用4位元組。

其在記憶體中分配的位置圖如下。

1、堆(heap)

存放著由操作malloc/free,new/delete分配/釋放的記憶體(不太安全的記憶體管理方式)。堆可以動態地擴充套件和收縮,這個區域通常較大,並向高位址擴充套件。動態記憶體的生存期人為決定,使用靈活。缺點是容易造成記憶體洩漏(memory leakage),頻繁操作會產生大量記憶體碎片。

(1)、記憶體碎片(memory fragment)

記憶體碎片分為兩種:外部碎片和內部碎片。

①、外部碎片(external memory fragment)

外部碎片指的是還沒有被分配出去(不屬於任何程序),但由於太小了無法分配給申請記憶體空間的新程序的記憶體空閒區域。

外部碎片是出於任何已分配區域或頁面外部的空閒儲存塊。這些儲存塊的總和可以滿足當前申請的長度要求,但是由於它們的位址不連續或其他原因,使得系統無法滿足當前申請。

多道可變連續分配只有外部碎片。

②、內部碎片(internal memory fragment)
內部碎片就是已經被分配出去(能明確指出屬於哪個程序)卻不能被利用的記憶體空間;

內部碎片是處於區域內部或頁面內部的儲存塊。占有這些區域或頁面的程序並不使用這個儲存塊。而在程序占有這塊儲存塊時,系統無法利用它。直到程序釋放它,或程序結束時,系統才有可能利用這個儲存塊。

單道連續分配只有內部碎片。多道固定連續分配既有內部碎片,又有外部碎片。

③、記憶體碎片減少的方法(solutions)

採用控制頁邊界對齊記憶體位元組對齊、將相鄰空閒記憶體塊連線起來、記憶體池等先進的記憶體管理機制。

2、棧(stack)

存放函式的引數值區域性變數,函式執行結束時會被自動釋放。棧記憶體分配運算內置於處理器的指令集中,效率高,但是容量有限。(棧方便用來儲存/恢復呼叫現場,可以把其看成乙個暫時儲存和交換資料的區域)

3、bss段(block started by symbol segment)

用來存放程式未初始化的全域性變數。不儲存在硬碟上,只是記錄資料所需空間的大小,程式開始執行之前,由核心進行初始化為0。bss段屬於靜態記憶體分配,即程式一開始就將其清零了。

4、資料段(data segment)

用來存放程式已初始化的全域性變數。資料段屬於靜態記憶體分配。其中static靜態變數存放在資料段中,而非棧區。

5、**段(code segment/text segment)

用來存放程式執行**。這部分區域的大小在程式執行前就已經確定,通常為唯讀(某些架構也允許**段為可寫,即允許修改程式),也有可能包含一些唯讀的常量,例如字串常量等。

如下所示,假如系統的資料儲存方式為小端模式(little endian),三個輸出應該是什麼?

#include

struct data

*example;

intmain

(int argc,

char

* ar**)

; example =

(struct data*

)num;

printf

("%x %x %x"

, example-

>a, example-

>b, example-

>c)

;system

("pause");

return0;

}

輸出結構是 0x0201 0x03 0x0605,這是為什麼呢?看下面的資料存放圖。

可以得出結構體中16位的a等於0x0201,8位的b等於0x03,16位的c等於0x0605。由於記憶體對齊,成員b只用到了低位元組0x03,0x04就被捨棄了(實際上還存在記憶體裡,但用不到,除非在b的位址加上一位元組偏移,如使用*(&(example->b)+1)就能讀到0x04)。

有關記憶體對齊的問題

1 某個成員距離首位置的偏移量最小是該成員大小的一倍。2 所有成員的大小之和應該是最大成員大小的整數倍。為什麼要記憶體對齊?點這裡 來段 解釋下 我們接下來就來解釋為什麼stu1和stu2分別是8和12,主要還是我們的兩個規則 注意 下面的表示方法,例如short b 就會在兩個位元組中填b,表示占...

個人有關記憶體的思考

對於應用程式而言,記憶體中儲存區域大致有堆 棧 靜態區域三個部分。系統在分配記憶體的時候,會在記憶體中尋找乙個能夠滿足申請大小的區域進行標記,並返回此區域的大小。在應用程式執行時,系統為應用程式分配的只是虛擬的位址空間,並不是實際的物理儲存器。這就需要給程序預定的區域 位址空間 調撥物理儲存器 記憶...

筆試題中有關樹的問題彙總

樹 tree 是一種簡單的非線性結構。所有資料元素之間有明顯的層次特性。根節點 沒有父節點的節點。葉子節點 沒有子節點的節點。節點的度 乙個節點所擁有的後件個數稱為該節點的讀。樹的度 所有節點中最大的度。樹的深度 樹的最大層次。二叉樹是一種每乙個節點最多有兩顆子樹的樹。估計這一特性,能夠計算二叉樹的...