程序師世界是廣大編程愛好者互助、分享、學習的平台,程序師世界有你更精彩!
首頁
編程語言
C語言|JAVA編程
Python編程
網頁編程
ASP編程|PHP編程
JSP編程
數據庫知識
MYSQL數據庫|SqlServer數據庫
Oracle數據庫|DB2數據庫
 程式師世界 >> 編程語言 >> C語言 >> C++ >> 關於C++ >> C++編程中new運算符的應用進修教程

C++編程中new運算符的應用進修教程

編輯:關於C++

C++編程中new運算符的應用進修教程。本站提示廣大學習愛好者:(C++編程中new運算符的應用進修教程)文章只能為提供參考,不一定能成為您想要的結果。以下是C++編程中new運算符的應用進修教程正文


new運算符用作從自在存儲為 type-name 的對象或對象數組分派內存,並將已恰當分類的非零指針前往到對象。

[::] new [placement] new-type-name [new-initializer]
[::] new [placement] ( type-name ) [new-initializer]

備注
假如不勝利,則 new 將前往零或激發異常;有關具體信息,請參閱 new 和 delete 運算符。 經由過程編寫自界說異常處置例程並挪用 _set_new_handler 運轉庫函數(以您的函數稱號作為其參數),可以更改此默許行動。
有關若何在托管堆上創立對象的信息,請參閱 gcnew。
應用 new 為 C++ 類對象分派內存時,將在分派內存後挪用對象的結構函數。
應用 delete 運算符可消除分派應用 new 運算符分派的內存。
以下示例先分派然後釋放一個二維字符數組,數組的年夜小為 dim x 10。 在分派多維數組時,除第一個維度以外的一切維度必需是盤算成果為正值的常量表達式;最左邊的數組維度可所以盤算成果為正值的任何表達式。 在應用 new 運算符分派數組時,第一個維度可為零 - new 運算符將前往一個獨一指針。

char (*pchar)[10] = new char[dim][10];
delete [] pchar;

type-name 不克不及包括 const、volatile、類聲明或列舉聲明。 是以,以下表達式長短法的:

volatile char *vch = new volatile char[20];

new 運算符不會分派援用類型,由於這些類型不是對象。
new 運算符沒法用於分派函數,但可用於分派指向函數的指針。 上面的示例為前往整數的函數分派然後釋放一個包括 7 個指針的數組。

int (**p) () = new (int (*[7]) ());
delete *p;

假如應用不帶任何額定參數的 new 運算符,並用 /GX、/EHa 或 /EHs 選項停止編譯,則編譯器將在結構函數激發異常時生成代碼來挪用運算符 delete。
以以下表描寫了 new 的語法元素:
placement
假如重載 new,則供給了一種傳遞附加參數的方法。
type-name
指定要分派的類型;它可所以內置類型,也能夠是用戶界說的類型。 假如類型標准異常龐雜,則可用括號將其括起來以強迫實行綁定次序。
initializer
為初始化對象供給值。 不克不及為數組指定初始值設定項。 僅當類具有默許結構函數時,new 運算符才會創立對象的數組。
示例
上面的代碼示例分派類 CName 的一個字符數組和一個對象,然後釋放它們。

// expre_new_Operator.cpp
// compile with: /EHsc
#include <string.h>

class CName {
public:
  enum {
   sizeOfBuffer = 256
  };

  char m_szFirst[sizeOfBuffer];
  char m_szLast[sizeOfBuffer];

public:
  void SetName(char* pszFirst, char* pszLast) {
   strcpy_s(m_szFirst, sizeOfBuffer, pszFirst);
   strcpy_s(m_szLast, sizeOfBuffer, pszLast);
  }

};

int main() {
  // Allocate memory for the array
  char* pCharArray = new char[CName::sizeOfBuffer];
  strcpy_s(pCharArray, CName::sizeOfBuffer, "Array of characters");

  // Deallocate memory for the array
  delete [] pCharArray;      
  pCharArray = NULL;

  // Allocate memory for the object
  CName* pName = new CName;
  pName->SetName("Firstname", "Lastname");

  // Deallocate memory for the object
  delete pName;
  pName = NULL;
}

假如應用 new 運算符的放置新情勢(帶有參數和分派年夜小的情勢),假如結構函數激發異常,則編譯器不支撐 delete 運算符的放置情勢。 例如:

// expre_new_Operator2.cpp
// C2660 expected
class A {
public:
  A(int) { throw "Fail!"; }
};
void F(void) {
  try {
   // heap memory pointed to by pa1 will be deallocated
   // by calling ::operator delete(void*).
   A* pa1 = new A(10);
  } catch (...) {
  }
  try {
   // This will call ::operator new(size_t, char*, int).
   // When A::A(int) does a throw, we should call
   // ::operator delete(void*, char*, int) to deallocate
   // the memory pointed to by pa2. Since
   // ::operator delete(void*, char*, int) has not been implemented,
   // memory will be leaked when the deallocation cannot occur.

   A* pa2 = new(__FILE__, __LINE__) A(20);
  } catch (...) {
  }
}

int main() {
  A a;
}

初始化應用 new 運算符分派的對象
可選的 initializer 字段包括在 new 運算符的語法中。 如許便可以應用用戶界說的結構函數來初始化新對象。 有關若何履行初始化的具體信息,請參閱初始值設定項。 以下示例演示若何將初始化表達式與 new 運算符一路應用:

// expre_Initializing_Objects_Allocated_with_new.cpp
class Acct
{
public:
  // Define default constructor and a constructor that accepts
  // an initial balance.
  Acct() { balance = 0.0; }
  Acct( double init_balance ) { balance = init_balance; }
private:
  double balance;
};

int main()
{
  Acct *CheckingAcct = new Acct;
  Acct *SavingsAcct = new Acct ( 34.98 );
  double *HowMuch = new double ( 43.0 );
  // ...
}

在此示例中,應用 CheckingAcctnew 運算符分派了 對象,但未指定默許初始化。 是以,挪用了類的默許結構函數 Acct()。 然後,以雷同的方法分派了對象 SavingsAcct,只不外將它顯式初始化為 34.98。 因為 34.98 是類型 double,是以挪用了采取該類型的參數的結構函數來處置初始化。 最初,將非類類型 HowMuch 初始化為 43.0。
假如對象是類類型,而且該類具有結構函數(如後面的示例所示),則僅當知足以下前提之一時,new 運算符能力初始化該對象:
初始值設定項中供給的參數與結構函數的參數分歧。
該類有一個默許結構函數(可在沒有參數的情形下挪用的結構函數)。
拜訪掌握和二義性掌握依據operator new多義性和應用特別成員函數的初始化中所述的規矩對 和結構函數履行。
在應用 new 運算符分派數組時,沒法對每一個元素履行顯式初始化;只挪用了默許結構函數(假如有)。 有關具體信息,請參閱默許參數。
假如內存分派掉敗(operator new 的前往值為 0),則不履行初始化。 這可避免測驗考試初始化不存在的數據。
與函數挪用一樣,不決義初始化表達式的盤算次序。 另外,您不該期望這些表達式能在履行內存分派前完整盤算。 假如內存分派掉敗,而且 new 運算符前往零,則能夠不會完整盤算初始值設定項中的某些表達式。
應用 new 運算符分派的對象的生計期
在加入分派有 new 運算符的對象的界說規模時,將不會燒毀這些對象。 因為 new 運算符將前往指向其所分派的對象的指針,是以法式必需應用適合的規模界說指針能力拜訪這些對象。 例如:

// expre_Lifetime_of_Objects_Allocated_with_new.cpp
// C2541 expected
int main()
{
  // Use new operator to allocate an array of 20 characters.
  char *AnArray = new char[20];

  for( int i = 0; i < 20; ++i )
  {
    // On the first iteration of the loop, allocate
    // another array of 20 characters.
    if( i == 0 )
    {
      char *AnotherArray = new char[20];
    }
  }

  delete [] AnotherArray; // Error: pointer out of scope.
  delete [] AnArray;   // OK: pointer still in scope.
}

在下面的示例中,指針 AnotherArray 一旦超越規模,將沒法再刪除對象。

new 的任務方法
allocation-expression(包括 new 運算符的表達式)履行三類操作:
定位並保存要分派的對象的存儲。 此階段完成後,將分派准確的存儲量,但它還不是對象。
初始化對象。 初始化完成後,將為成為對象的已分派存儲顯示足夠的信息。
前往指向派生自 new-type-name 或 type-name 的指針類型的對象的指針。 法式應用此指針來拜訪比來分派的對象。
new 運算符挪用函數 operator new。 關於任何類型的數組和不屬於 class、struct 或 union 類型的對象,挪用全局函數 ::operator new 來分派存儲。 類類型對象可基於每一個類界說其本身的 operator new 靜態成員函數。
當編譯器碰到用於分派 type 類型的對象的 new 運算符時,它將收回對 type::operator new( sizeof( type ) ) 的挪用;或許,假如不存在用戶界說的 operator new,則挪用 ::operator new( sizeof( type ) )。 是以,new 運算符可認為對象分派准確的內存量。

  1. 上一頁:
  2. 下一頁:
Copyright © 程式師世界 All Rights Reserved