1. 程式人生 > 其它 >07-動態記憶體分配

07-動態記憶體分配

技術標籤:C++

動態物件建立

產生條件

當建立陣列的時候,總是需要提前預定陣列的長度,然後編譯器分配預定長度的陣列空間,在使用陣列的時,會有這樣的問題,陣列也許空間太大了,浪費空間,也許空間不足,所以對於陣列來講,如果能根據需要來分配空間大小再好不過。所以動態的意思意味著不確定性

C動態分配記憶體

為了解決這個普遍的程式設計問題,在執行中可以建立和銷燬物件是最基本的要求。c早就提供了動態記憶體分配(,函式malloc和free可以在執行時從堆中分配單元。

程式碼示例

int *p = (int*) malloc( sizeof(int) * 10 );  //分配10個int型的記憶體空間
free(p); //釋放記憶體

缺陷:

1、程式設計師必須確定物件的長度。

2、malloc返回一個void指標,c++不允許將void賦值給其他任何指標,必須強轉。

3、 malloc可能申請記憶體失敗,所以必須判斷返回值來確保記憶體分配成功。

4、在使用物件之前必須記住對它初始化,建構函式不能顯示呼叫初始化(建構函式是由編譯器呼叫),使用者有可能忘記呼叫初始化函式。

C++動態分配記憶體

C++中通過new關鍵字進行動態記憶體申請,當用new建立一個物件時,它就在堆裡為物件分配記憶體並呼叫建構函式完成初始化。

C++中的動態記憶體申請是基於型別進行的

C++中delete關鍵字用於記憶體釋放。delete表示式先呼叫解構函式,然後釋放記憶體

。正如new表示式返回一個指向物件的指標一樣,delete需要一個物件的地址。delete只適用於由new建立的物件。

變數申請基本語法

Type* pointer = new Type; // 記憶體申請

delete pointer; // 記憶體釋放

程式碼示例

#include <iostream>
#include <cstring>

using namespace std;
// 建立Person類
class Person{
public:
    // 定義成員變數
    char* pName;
    int mAge;

    // 無參構造
    Person
(){ cout << "無參建構函式!" << endl; pName = (char*)malloc(strlen("undefined") + 1); strcpy(pName, "undefined"); mAge = 0; } // 代參構造 Person(char* name, int age){ cout << "有參建構函式!" << endl; pName = (char*)malloc(strlen(name) + 1); strcpy(pName, name); mAge = age; } void ShowPerson(){ cout << "Name:" << pName << " Age:" << mAge << endl; } ~Person(){ cout << "解構函式!" << endl; if (pName != NULL){ delete pName; pName = NULL; } } }; // 呼叫函式 void test(){ // 建立物件 Person* person1 = new Person; Person* person2 = new Person("John",33); // 物件呼叫方法 person1->ShowPerson(); person2->ShowPerson(); // 釋放記憶體 delete person1; delete person2; } int main() { // 呼叫函式 test(); return 0; }

程式碼執行結果

陣列申請基本語法

當建立一個物件陣列的時候,必須對陣列中的每一個物件呼叫建構函式,除了在棧上可以聚合初始化,必須提供一個預設的建構函式

Type* pointer = new Type[N]; // 陣列申請
delete[] pointer; // 記憶體釋放

程式碼示例

#include <iostream>
/**
 * 利用new在堆區開闢陣列
 */
using namespace std;

class Person
{
public:
    Person()
    {
        cout << "Person的預設建構函式呼叫" << endl;
    }

    Person(int a )
    {
        cout << "Person的有參建構函式呼叫" << endl;
    }

    Person(const Person & p)
    {
        cout << "Person的拷貝建構函式呼叫" << endl;
    }

    ~Person()
    {
        cout << "Person的解構函式呼叫" << endl;
    }
};

int main() {
    // 建立陣列物件
    int * intArray = new int[10];
    char * charArray =  new char[100];

    //如果利用new在堆區開闢 自定義型別資料的陣列,必須有預設建構函式
    Person * personArray = new Person[3];

    delete [] personArray;

    //如果在棧上開闢陣列,可以沒有預設建構函式
    //Person pArray[2] = { Person(1), Person(2) };
    //delete personArray;
    return 0;
}

程式執行結果

new和malloc區別

new關鍵字

new關鍵字是C++的一部分。
new以具體型別為單位進行記憶體分配。
new在申請單個型別變數時可進行初始化

malloc函式

mallloc是由C庫提供的函式。
malloc 以位元組為單位進行記憶體分配。
malloc不具備記憶體初始化的特性。