复制构造函数通常在如下情形会被调用:
(1)显式复制构造;
(2)对象值传递;
(3)返回对象值,返回前先要拷贝到临时无名对象上。
最近和人讨论一个奇怪的现象:他的代码中存在值传递对象和返回对象值两种情况,他发现在VC6.0环境下,如果存在析构函数,会产生4次复制构造,但是如果析构函数注释掉其他代码不变的情况下,只调用三次复制构造。后来我们在g++, VC高版本进行了测试,发现在其他VC编译环境下,始终只执行三次复制构造。
我对此事的理解是,C++标准允许编译过程中对代码优化,比方说:当返回的对象值同时作为参数值传递给某个函数时,编译器可以进行一些优化,在现代C++编译器中,基本上进行了优化。
而VC6.0是个烂东西,狂烂狂老的东西,在友元、模板等很多地方对C++标准支持得非常不好!我猜测它在这一块也做了优化,但是是不彻底的优化,具体优化方法:
(1)如果返回对象同时作为函数值传递参数传进去,如果这个对象类没有析构函数,编译器在这种情况下进行了优化,减少了一次对象复制。
(2)如果对象的类存在析构函数,编译器认为此时优化存在不安全因素,因此未做优化。
瞎猜测罢了,其实没有必要去推敲这些东西,VC6.0早就应该扔到垃圾堆了。