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
的使用顺序全局对象的构造顺序是不确定的