1. 程式人生 > >C++學習10:使用new分配記憶體

C++學習10:使用new分配記憶體

在C++中,可以沿用C中的malloc分配記憶體,也可以使用new運算子。今天就來學習使用new分配記憶體。

new的作用和使用方法:

new的作用在於可以在程式執行階段動態分配記憶體,記憶體的大小在執行時根據需要確定,從而高效利用記憶體空間。

new的使用方法如下:

typeName* pointer_name = new typeName

使用時使用者需要指定型別(指標型別和要開闢的記憶體儲存的資料型別),new可以自動找到一個正確長度的記憶體塊,並返回記憶體塊的地址。分配記憶體失敗時,預設丟擲bad_alloc異常。

比如:

int* p = new int;

這裡指定了int型,new會自動找到適合儲存int的記憶體,將地址返回賦給指標p。

此時,使用new開闢的記憶體塊只能通過指標p來訪問,這塊記憶體是未命名的。

要注意一點:new分配的記憶體位於堆(heap)或自由儲存區(free store)中,而常規變數分配的記憶體是在棧(stack)中。堆和棧的區別在於:棧(stack)由編譯器自動分配釋放,而堆(heap)一般由程式設計師分配釋放,若程式設計師不釋放,程式結束時可能由OS回收。

在使用new時,釋放記憶體的方法就是delete。

使用delete釋放記憶體

delete可以釋放記憶體供其他部分使用。方法十分簡單,在delete後加指向待釋放記憶體的指標即可,比如:

    int* p = new
int; delete p;

這樣就可以釋放掉通過new為開闢的記憶體了。

需要注意的是,delete只能釋放由new開闢的記憶體。注意以下三種情況:
1、如果試圖釋放常規變數宣告分配的記憶體,會報錯。如:

    //delete不能釋放常規變數宣告分配的記憶體
    int i =3;
    int* p = &i;

2、如果試圖釋放已被delete釋放的記憶體,會報錯。如:

    //delete釋放後,p指標不會被刪除,而是重新指向了一處新的地址。
    int* p = new int;
    delete p;
    delete p;

3、delete可以釋放空指標,這是安全的,不報錯。如:

    int* p = NULL;
    delete p;
    delete p;

使用new建立動態陣列

之前說了,new可以在執行時動態分配記憶體,這一作用的具體體現就是建立動態陣列。
如:

int data[100]={0};

這裡宣告一個int型陣列,長度為100,其記憶體空間在編譯時已經分配好了。無論這個陣列在實際執行中使用了多少,總是會佔用那部分記憶體空間。

而如果使用new建立動態陣列:

int* p = new int [100];   //p指向動態陣列的首地址

其記憶體是在執行時在分配的,當不使用時可以使用delete釋放掉。釋放動態陣列時需要加[]:

    int* p = new int [100];
    delete [] p;

如果不加[],但不會報錯,結果是不確定的,不要這樣做。

這裡貼一個c++ primer plus中的一個例子,個人感覺十分巧妙。

#include<iostream>  
#include<cstring>

using namespace std;  
char* getname(void);

int main(void)  
{   
    char* name;
    name = getname();
    cout << "The length of " << name << " is " << strlen(name) << endl;
    delete [] name;

    name = getname();
    cout << "The length of " << name << " is " << strlen(name) << endl;
    delete [] name;

    system("pause");
}  

char* getname()
{
    char temp[80];
    cout << "Enter last name: ";
    cin >> temp;
    char* pn = new char[strlen(temp)+1];
    strcpy(pn, temp);

    return pn;
}

可以看到,動態陣列實際是在getname函式中建立的。通過臨時字元陣列temp儲存輸入的字串,通過strlen(temp)+1計算需要的字串長度提供給new,實現開闢對應大小的記憶體空間,並通過strcpy(pn, temp)將字串複製到新開闢的記憶體處。

這樣做可以每次都建立剛好能夠儲存輸入字串的記憶體塊,在讀取大量字串的程式中,可以節省大量記憶體。

需要注意的是,這裡new和delete放在了不同的函式中,這樣是可以的,但容易忘記delete。

相關推薦

C++學習10使用new分配記憶體

在C++中,可以沿用C中的malloc分配記憶體,也可以使用new運算子。今天就來學習使用new分配記憶體。 new的作用和使用方法: new的作用在於可以在程式執行階段動態分配記憶體,記憶體的大小在執行時根據需要確定,從而高效利用記憶體空間。 new

C++ Primer Plus書之--C++指標及使用new分配記憶體,使用delete釋放記憶體

先來個簡單的程式初步認識一下指標  #include "iostream" using namespace std; int main() { // 定義一個int型變數 int num = 123; // 定義一個int型指標變數 int * p_num; // 指標指向

學習10訊息釋出器和訂閱器(C++)

因為我不會python,所以只能用C++了  - -# 1 節點 ROS中把可執行檔案叫做【節點】。 去剛才的beginner_tutorial(眼花了,單詞打沒打錯?……)目錄下,新建src資料夾,裡面寫一個 talker.cpp 裡面程式碼如下 /* * Copyr

C++ 處理new分配記憶體失敗

轉自:http://www.51testing.com/html/70/n-827070.html在C++語言中,我們經常會使用new給一個物件分配記憶體空間,而當記憶體不夠會出現記憶體不足的情況。C++提供了兩中報告方式:  1、丟擲bad_alloc異常來報告分配失敗; 

VS2010 C++ 學習筆記(二) 記憶體管理 new delete

記憶體的申請與示範  ***********************************************************************************

Spark機器學習(10)ALS交替最小二乘算法

mllib 測試 con 相互 idt color ted 個人 使用 1. Alternating Least Square ALS(Alternating Least Square),交替最小二乘法。在機器學習中,特指使用最小二乘法的一種協同推薦算法。如下圖所示,u表

C#學習筆記預處理指令

copy erro log com 學習 tco endif href 指定 C#和C/C++一樣,也支持預處理指令,下面我們來看看C#中的預處理指令。 #region 代碼折疊功能,配合#endregion使用,如下: 點擊後如下: 條件預處理 條件預處

處理new分配記憶體失敗情況

轉自:http://www.51testing.com/html/70/n-827070.html 在C++語言中,我們經常會使用new給一個物件分配記憶體空間,而當記憶體不夠會出現記憶體不足的情況。C++提供了兩中報告方式:   1、丟擲bad_alloc異常來報告分配失敗;   2、返回空指標,而不

C++學習筆記(十)異常

10.異常處理 C++具有強大的擴充套件能力,同時也大大增加了產生錯誤的可能性。在程式設計時,不能忽略異常處理。處理異常的方法多種多樣。錯誤處理程式碼分佈在整個系統程式碼中,在任何可能出錯的地方都進行異常處理,閱讀程式碼時可以直接看到異常處理的情況,但是引起的程式碼膨脹將不

機器學習10Tips of DNN——啟用函式選擇

一、Training和Testing情形 overfitting:Training Data上表現良好,Testing Data表現不好。 Training失敗:梯度消失等情形。 如下的例子屬於Training失敗,並非overfitting: 雖然層數增加導致訓練結果變差,但

C++學習筆記(三)記憶體模型、名稱空間、物件和類

    1、標頭檔案中通常包含的內容:函式原型、使用#define和const定義的符號常量、結構宣告、類宣告、模板宣告、行內函數     2、同樣可以使用條件編譯     3、靜態持續變數:外部連結性、內部連結性、無連結性靜態持續變數:外部連結性、內部連結性、無連結性         外部連結性:在程式碼塊

C++學習筆記-DLL中動態記憶體管理

動態記憶體管理 在dll中malloc的記憶體,必須在dll中free 注:這是由Windows自己的特點決定! 如果 a 編譯成靜態庫,有下面兩種解決方法: 1.b.dll 和 c.dll 使用

c/c++實現的一個動態分配記憶體的結構體陣列(類似vector)

這個陣列可以向裡面插入任何型別,包括自定義型別, 程式只是實現了基本功能,還有待完善, 首先初始化,然後就可以插入資料了, 當儲存單元不足的時候就自動增加儲存單元 由於總的風格是c, 所以看著很是彆扭, 有空了把全部改成c++風格的; 說有空就有空了,改成了c++風格了,

c++學習記錄operator = 過載

  《effective c++》的確是一本神書,閱讀起來的感覺可以用酣暢淋漓來形容,似乎很多以前沒有在意的小細節都變得豁然開朗了起來,在條款10中,scott建議我們過載操作符’=’時,返回一個*this的引用。   賦值,我們往往可以寫作連鎖形式:   

C++知識點10建構函式和解構函式

建構函式: 生成物件時呼叫建構函式 生成派生類物件時先呼叫基類建構函式在呼叫派生類建構函式 #include <iostream> using namespace std; class base { public: base(){

C++學習之一建構函式

建立一個物件時,通常要對物件的資料成員進行初始化的工作,但是類的資料成員不能在宣告類時初始化的(除非是static const int型)。如果一個類中所有的資料成員都是public的,則可以在定義物件時對資料成員進行初始化,如: class Student { publ

使用new分配記憶體、建立動態陣列、

1、使用new來分配記憶體 程式設計師需要告訴new,需要為哪種資料型別分配記憶體;new將找到一個長度正確的記憶體塊,並返回該記憶體塊的地址, 程式設計師的責任是將改地址賦給一個指標。 int *pn = new int; new int告訴程式,需要儲存i

C++學習14使用typedef定義函式指標型別

最近在HM中遇到了typedef函式指標,現在來學習一下。 1.函式指標 直接從例子入手,首先來看一個簡單的函式指標: #include"iostream" using namespace std; int cal_max(int x,in

C語言練習題】動態分配記憶體

《C和指標》練習題11.11   問題 編寫一個函式,從標準輸入讀取一列整數,把這些值儲存於一個動態分配的陣列中並返回這個陣列。函式通過觀察EOF判斷輸入列表是否結束。陣列的第一個數是陣列包含的值的個數,他的後面就是這些整數值   程式碼 #inclu

2018.11.26 C++學習錯誤類的建構函式錯誤

對類的建構函式寫實現方法時,對類成員賦值時,不要用資料型別名。好像很蠢,但是我犯了這個錯誤,導致類物件顯示結果不對,還找了半天錯誤。 class Sales { private: double sales[QUARTERS]; double average; double max; doub