C++創建對象的兩種方式


C++創建對象有兩種方式,在棧上創建對象(Objects on the Stack)和在堆上創建對象(Objects on the Heap)。

假設我們有以下的類:

 1 #include <string>
 2 using std::string;
 3 
 4 class SpreadsheetCell{
 5 public:
 6     void setValue(double inValue);
 7     double getValue();
 8     void setString(string inString);
 9     string getString();
10 
11 protected:
12     string doubleToString(double inValue);
13     double stringToDouble(string inString);
14 
15     double mValue;
16     string mString;
17 };

以及如下的cpp文件:

 1 #include "stdafx.h"
 2 #include "SpreadsheetCell.h"
 3 #include <iostream>
 4 #include <sstream>
 5 
 6 using namespace std;
 7 
 8 void SpreadsheetCell::setValue(double inValue){
 9     mValue = inValue;
10     mString = doubleToString(mValue);
11 }
12 
13 double SpreadsheetCell::getValue(){
14     return mValue;
15 }
16 
17 void SpreadsheetCell::setString(string inString){
18     mString = inString;
19     mValue = stringToDouble(mString);
20 }
21 
22 string SpreadsheetCell::getString(){
23     return mString;
24 }
25 
26 string SpreadsheetCell::doubleToString(double inValue){
27     ostringstream ostr;
28     ostr<<inValue;
29     return ostr.str();
30 }
31 
32 double SpreadsheetCell::stringToDouble(string inString){
33     double temp;
34 
35     istringstream istr(inString);
36 
37     istr>>temp;
38     if(istr.fail() || !istr.eof()){
39         return (0);
40     }
41 
42     return temp;
43 }

 

1. 在棧上創建對象(Objects on the Stack):

語法:

1 ClassName ObjName1, ObjName2(parameter01)// But never OjbName()

顧名思義,用這種方法創建的對象,內存分配到棧里(Stack)。使用 “.” 非 “->” 調用對象的方法。當程度離開對象的使用范圍(如方法結束,一個程度塊的最后{}),范圍內的棧中的對象會自動刪除,內存自動回收。這是創建對象最簡單的方式,與“int x = 0;”是一樣的。如下面例子:

SpreadsheetCell myCell, anotherCell;
myCell.setValue(6);
anotherCell.setValue(myCell.getValue());
cout << “cell 1: “ << myCell.getValue() << endl;
cout << “cell 2: “ << anotherCell.getValue() << endl;

//destroy:
int main(int argc, char** argv)
{
  SpreadsheetCell myCell(5);
  if (myCell.getValue() == 5) {
    SpreadsheetCell anotherCell(6);
  } // anotherCell is destroyed as this block ends.
  cout << “myCell: “ << myCell.getValue() << endl;
  return (0);
} // myCell is destroyed as this block ends.

//destroy in reverse order:
{
  SpreadsheetCell myCell2(4);
  SpreadsheetCell anotherCell2(5); // myCell2 constructed before anotherCell2
} // anotherCell2 destroyed before myCell2

 

2.在堆上創建對象(Objects on the Heap):

語法:

ClassName *obj1 = new ClassName();

ClassName *obj2 = new ClassName(parameter);

delete obj1;

delete obj2;

用這種方法創建的對象,內存分配到堆里(Heap)。一般使用“->” 調用對象的方法。箭頭操作符”->"將解引用(dereferencing*)和成員使用(member access.)結合起來,下例兩個輸出,效果等價:

 1 int _tmain(int argc, _TCHAR* argv[])
 2 {
 3     SpreadsheetCell *myCellp = new SpreadsheetCell();
 4 
 5     myCellp->setValue(3.7);
 6 
 7     cout<<"cell 1: "<<myCellp->getValue()<<" "<<myCellp->getString()<<endl;
 8 
 9     cout<<"cell 1: "<<(*myCellp).getValue()<<" "<<(*myCellp).getString()<<endl;
10 
11     delete myCellp;
12     return 0;
13 }

在堆中的對象不會自動刪除,內存不會自動回收,所以new一個對象使用完畢,必須調用delete,釋放內存空間。也就是說,new和delete必須成對出現。

 

順便提提,內存的分配方式有三種
      (1)從靜態存儲區域分配。內存在程序編譯的時候就已經分配好,這塊內存在程序的整個運行期間都存在。例如全局變量,static 變量。 
      (2)  在棧上創建。在執行函數時,函數內局部變量的存儲單元都可以在棧上創建,函數執行結束后在將這些局部變量的內存空間回收。在棧上分配內存空間效率很高,但是分配的內存容量有限。
       (3) 從堆上分配的。程序在運行的時候用 malloc 或 new 申請任意多少的內存,程序員自己負責在何時用 free 或 delete 釋放內存。

 

參考:

Professional C++, chapter 8

http://blog.csdn.net/cscmaker/article/details/7019977


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM