第一次,代码如下所示:
#include "stdafx.h"
#include<iostream>
using namespace std;
class Test{
public:
explicit Test(int);
~Test();
//Test(Test&);
int varInt;
};
Test::Test(int temp){
varInt = temp;
cout << "call Test::constructor\n";
}
Test::~Test(){
cout << "call Test::destructor\n";
}
/*Test::Test(Test&temp){
varInt = temp.varInt;
cout << "call Test::copy constructor\n";
}*/
void func(Test temp){
cout << "call func\n";
}
int _tmain(int argc, _TCHAR* argv[])
{
func(Test(1));
return 0;
}
输出:
call Test::constructor
call func
call Test::destructor
call Test::destructor
这让我感到困惑,因为只创建了一个对象(作为func的参数),但是在函数结束后调用了两个析构函数。 我开始怀疑,这是因为默认的复制构造函数被调用了吗?所以我写了复制构造函数的定义,这让事情变得更加奇怪。 在我将上面提到的注释掉的代码(即复制构造函数的定义)添加到类中后,输出变为如下所示:
输出:
call Test::constructor
call func
call Test::destructor
事情变得恰到好处。 有人可以向我解释这个现象吗?非常感谢你。
答案 0 :(得分:3)
编辑添加:顺便提一句,在您的带有显式复制构造函数的版本中,构造函数在获取非常量引用时不常见。这实际上意味着它无论如何都无法使用,因为非常量引用无法绑定到临时Test(1)
。我认为这种奇怪可能与编译器执行复制省略的原因有关。如果更改构造函数以获取常量引用,则作为隐式声明的复制构造函数,您可能会看到您期望的行为,并调用显式复制构造函数并且两次调用析构函数。 (但这只是我的猜测;你必须尝试看看!)
答案 1 :(得分:1)
你有两个Test类对象。由于您按值传递参数,因此在main函数中显式构造一个参数,另一个使用默认复制构造函数构造,因为您的复制构造函数已被注释掉。两个对象都被破坏了。一个在func()的出口处,另一个在main()的出口处。因此有两个析构函数调用。