从复制构造函数调用构造函数时,它也调用析构函数

时间:2016-09-29 16:49:07

标签: c++ c++11 constructor copy-constructor

我制作了一个使用复制构造函数来复制对象的程序。在复制构造函数中,我调用了构造函数来创建内存并复制内容。它在构造函数中成功完成,但在构造函数结束后立即调用析构函数并获取垃圾值。最后在main函数中如果我试图破坏新创建的对象,程序崩溃了。为什么它的表现如此?

这里是代码。

#include<iostream>
using namespace std;

class Test
{
    public:
    int a;
    int *p;

    Test(int a,int b,int c)
    {
        this->a=a;
        p=new int[2];
        p[0]=b;
        p[1]=c;
        cout<<"\n\n "<<this->a<<"   "<<this->p[0]<<"   "<<this->p[1];
    }
    Test(const Test &ob)
    {
        Test(ob.a,ob.p[0],ob.p[1]);
        cout<<"\n\n "<<this->a<<"   "<<this->p[0]<<"   "<<this->p[1];
    }
    void print()
    {
        cout<<"\n\n\n "<<a<<"   "<<p[0]<<"   "<<p[1];
    }
    ~Test()
    {
        cout<<"\n\n\n DESTRUCTOR CALLED "<<endl;
        delete [] p;
    }
};

int main()
{
    Test *ob1=new Test(2,3,4);
    cout<<"\n\n\n  ob2: new object";
    Test *ob2=new Test(*ob1);
    cout<<"\n\n\n ob1";
    (*ob1).print();
    cout<<"\n\n\n ob2";
    (*ob2).print();
    delete ob1;
    delete ob2;
    return 1;
} 

产生输出:

2 3 4

ob2:新对象 2 3 4

DESTRUCTOR CALLED

9968956 9968956 0

OB1

2 3 4

OB2

9968956 9968956 0

DESTRUCTOR CALLED

DESTRUCTOR CALLED

&#34;然后程序停止工作,即崩溃&#34; ....

我不知道在这种情况下会发生什么,但是PLZ解释了为什么在删除对象ob2时程序在这种情况下崩溃。 感谢

2 个答案:

答案 0 :(得分:4)

复制构造函数确实没有做任何事情。 let string = 'abbabcbdbabdbdbabababcbcbab'; let unique = [...new Set(string)]; 只是创建一个临时的Test(ob.a,ob.p[0],ob.p[1]);,它将立即被销毁。 Test的所有成员都没有初始化。

您想要delegate constructor,这是一个C ++ 11功能。

Test

答案 1 :(得分:0)

至少在这里有几个问题。

首先,int* p是指向单个整数的指针,但您将其视为指向整数数组的指针。 p[1]不一定是你拥有的记忆。

关于意外的析构函数调用,复制构造函数会创建一个临时的Test对象,当您退出复制构造函数的范围时,该对象会被销毁。这就是为什么在尝试从复制构造中创建新对象后,您会看到正确调用析构函数的原因。请参阅@ songyuanyao关于使用委托构造函数的答案。

此外,您对delete的来电无效,因为它们是在您致电return后发出的。

最后,正如风格一样,return 0;通常表示您的程序正常结束。 return <some_nonzero_number>;通常用于向调用者表明您的程序由于某些错误而结束。

编辑:p=new int(2*sizeof(int));仍然不是您在尝试使用p时要执行的操作。这只是创建一个指向单个整数的指针,其中整数的值为2 * 4 = 8。 要正确使用p,您可能意味着p = new int[2];在这种情况下,请记住在析构函数中使用delete [] p;