C++ 析构函数和复制构造函数调用..(为什么在这些时候调用它)
我有以下代码C++ 析构函数和复制构造函数调用..(为什么在这些时候调用它),c++,gcc,class,destructor,copy-constructor,C++,Gcc,Class,Destructor,Copy Constructor,我有以下代码 #include <iostream> using namespace std; class Object { public: Object(int id){ cout << "Construct(" << id << ")" << endl; m_id = id; } Object(const Object& obj){ cout <&
#include <iostream>
using namespace std;
class Object {
public:
Object(int id){
cout << "Construct(" << id << ")" << endl;
m_id = id;
}
Object(const Object& obj){
cout << "Copy-construct(" << obj.m_id << ")" << endl;
m_id = obj.m_id;
}
Object& operator=(const Object& obj){
cout << m_id << " = " << obj.m_id << endl;
m_id = obj.m_id;
return *this;
}
~Object(){
cout << "Destruct(" << m_id << ")" << endl;
}
private:
int m_id;
};
Object func(Object var) { return var; }
int main(){
Object v1(1);
cout << "( a )" << endl;
Object v2(2);
v2 = v1;
cout << "( b )" << endl;
Object v4 = v1;
Object *pv5;
pv5 = &v1;
pv5 = new Object(5);
cout << "( c )" << endl;
func(v1);
cout << "( d )" << endl;
delete pv5;
}
我对此有一些问题,首先,为什么objectv4=v1
调用复制构造函数,在打印(b)
后生成复制构造函数(1)
同样在打印了(c)
之后,复制构造函数又被调用了两次,我不确定这个函数是如何产生这个结果的
objectfunc(objectvar){returnvar;}
在这之后,Destruct(1)
被调用两次,然后打印(d)
很抱歉回答了这么长的问题,我把上面的问题弄糊涂了。至于第一个问题,
objectv4=v1
是对象v4(v1)的语法糖代码>,它显然调用了复制构造函数
第二个比较复杂。当按值向函数传递变量时,必须复制它们-因此需要调用复制构造函数。对象的副本也必须放在堆栈上调用方可以访问它的位置,因为传递给函数的副本在函数返回时不再存在。制作这两个副本后,参数将在从堆栈弹出时被销毁,返回值将被销毁,因为它的值未被使用。它们具有相同的ID,因为它们是v1
的副本
首先,我有一些问题
为什么对象v4=v1;呼叫副本
建造商和生产商
打印后复制构造(1)
第(b)款
尽管有=
符号,您仍在这里调用复制构造函数。请记住,您没有默认构造函数。您正在构造一个新的对象
,并使用v1
值对其进行初始化。你要做什么
cout << "( b )" << endl;
Object v4(0);
v4 = v1;
…我想这是你期待的
同样在打印(c)之后
再次调用复制构造函数
两次?我不确定这是怎么回事
函数用于生成该对象
func(对象变量){return var;}
这里,您通过值(而不是引用[&])传递var
,这意味着创建了对象的副本(一次对副本构造函数的调用)。然后返回另一个对象
(同样,不是引用),因此必须进行另一个副本(对副本构造函数的第二次调用)
在破坏(1)之后
在打印(d)之前调用两次
您刚才用复制构造函数创建的那些对象?它们只是超出了范围,它们的析构函数被调用
当您delete
v5
时,将调用其析构函数
然后到达main
函数的末尾,在堆栈上创建的三个对象
实例(v1
,v2
,v4
)到达其生命周期的末尾,并在堆栈展开时销毁
您可能已经注意到,析构函数调用的数量与构造函数调用的数量完全相同
Object v1(1);
// Construct(1)
自动堆栈变量的常规构造函数调用(在函数末尾销毁)
调用赋值运算符是因为v2已经创建(我们为它调用了构造函数),现在我们正在将一个现有对象赋值给另一个
cout << "( b )" << endl;
// ( b )
Object v4 = v1;
// Copy-construct(1)
调用堆对象的构造函数(使用delete
显式销毁)
非常感谢。还有一个问题,Destruct(1)
的最后3个输出是由于对象v1(1);,v2=v1,对象v4=v1代码>正确吗?而析构函数(5)
就在它被手动删除之前出现?您能解释一下最后4个析构函数调用吗?。
Object v1(1);
// Construct(1)
cout << "( a )" << endl;
// ( a )
Object v2(2);
// Construct(2)
v2 = v1;
// 2 = 1
cout << "( b )" << endl;
// ( b )
Object v4 = v1;
// Copy-construct(1)
Object *pv5;
pv5 = &v1;
pv5 = new Object(5);
// Construct(5)
cout << "( c )" << endl;
// ( c )
func(v1);
// Copy-construct(1) <br />
// Copy-construct(1) <br />
// Destruct(1) <br />
// Destruct(1) <br />
cout << "( d )" << endl;
// ( d )
delete pv5;
// Destruct(5)
} // end of main
// Destruct(1) <br />
// Destruct(1) <br />
// Destruct(1) <br />