十九、物件的構造順序
阿新 • • 發佈:2018-12-11
C++中的類可以定義多個物件,物件的構造順序是怎樣的?
1、物件的構造順序一
對於區域性物件:當程式執行流到達物件的定義語句時進行構造:物件定義->構造
#include <stdio.h> class Test { private: int mi; public: Test(int i) { mi = i; printf("Test(int i): %d\n", mi); } Test(const Test& obj) { mi = obj.mi; printf("Test(const Test& obj): %d\n", mi); } int getMi() { return mi; } }; int main() { int i = 0; Test a1 = i; // Test(int i): 0 while( i < 3 ) { Test a2 = ++i; // Test(int i): 1, 2, 3 } if( i < 4 ) { Test a = a1; // Test(const Test& obj): 0 } else { Test a(100); } return 0; }
int main() { int i = 0; Test a1 = i; // Test(int i): 0 while( i < 3 ) { Test a2 = ++i; // Test(int i): 1, 2, 3 } goto End: // if 語句被跳過,物件定義被跳過,兩個物件都不會被建立 if( i < 4 ) { Test a = a1; } else { Test a(100); } End: return 0; }
程式執行流和區域性物件的構造相關,非法改變程式執行流,會產生災難性錯誤
int main()
{
int i = 0;
Test a1 = i; // Test(int i): 0
while( i < 3 )
{
Test a2 = ++i; // Test(int i): 1, 2, 3
}
goto End:
Test a(100);
End:
printf("a.mi = %d\n", a.getMi()); // 報錯
return 0;
}
2、物件的構造順序二
對於堆物件:
- 當程式執行流到達
new
- 使用
new
建立物件將自動觸發建構函式的呼叫
考慮下面程式中的物件構造順序
int i = 0;
Test* a1 = new Test(i);
while(++i < 10)
if(i%2)
new Test(i);
if(i < 4)
new Test(*a1);
else
new Test(100);
也會受到goto語句的影響
3、物件的構造順序三
對於全域性物件:
- 物件的構造順序是不確定的
- 不同的編譯器使用不同的規則確定構造順序
#include "test.h"
Test t4("t4"); // t4的構造在main之前構造,和程式執行流無關
int main()
{
Test t5("t5");
}
儘量避開全域性物件的使用
4、小結
區域性物件的構造順序依賴於順序的執行流
堆物件的構造順序依賴於
new
的使用順序全域性物件的構造順序是不確定的