对象的析构函数导致崩溃 我是C++中的NOOB。我有一个无论如何也解决不了的问题。为了更好地理解类和重载运算符,我编写了一段代码: #include <iostream> #include <stdlib.h> #include <stdarg.h> using namespace std; class vectmy { public: int size; int *a; vectmy(int n,int val); ~vectmy (){delete[] a; //IF I DELETE THIS PROGRAM WORKS } vectmy & operator = (const vectmy &); }; vectmy::vectmy(int n,int val){ size=n; a = new int[ n+1 ]; for (int i=0;i<n;++i){ *(a+i)=val; } } vectmy& vectmy::operator= (const vectmy& param) { for (int i=0;i<3;++i) a[i]=param.a[i]; return *this; } vectmy operator+( vectmy left, vectmy right) { vectmy result = left; for (int i=0;i<3;++i) result.a[i]=result.a[i]+right.a[i]; return result; } int main() { int b1[3]={1,2,4}; vectmy d(3,2),b(3,4),c(3,0); c=(b+d); for (int j=0; j<3; ++j)cout<<c.a[j]<<' '<<endl; return 0; } #包括 #包括 #包括 使用名称空间std; 类向量{ 公众: 整数大小; int*a; 向量(int n,int val); ~vectmy(){delete[]a;//如果我删除了这个程序,它就会工作 } 向量和运算符=(常量向量和); }; vectmy::vectmy(int n,int val){ 尺寸=n; a=新整数[n+1]; 对于(int i=0;i

对象的析构函数导致崩溃 我是C++中的NOOB。我有一个无论如何也解决不了的问题。为了更好地理解类和重载运算符,我编写了一段代码: #include <iostream> #include <stdlib.h> #include <stdarg.h> using namespace std; class vectmy { public: int size; int *a; vectmy(int n,int val); ~vectmy (){delete[] a; //IF I DELETE THIS PROGRAM WORKS } vectmy & operator = (const vectmy &); }; vectmy::vectmy(int n,int val){ size=n; a = new int[ n+1 ]; for (int i=0;i<n;++i){ *(a+i)=val; } } vectmy& vectmy::operator= (const vectmy& param) { for (int i=0;i<3;++i) a[i]=param.a[i]; return *this; } vectmy operator+( vectmy left, vectmy right) { vectmy result = left; for (int i=0;i<3;++i) result.a[i]=result.a[i]+right.a[i]; return result; } int main() { int b1[3]={1,2,4}; vectmy d(3,2),b(3,4),c(3,0); c=(b+d); for (int j=0; j<3; ++j)cout<<c.a[j]<<' '<<endl; return 0; } #包括 #包括 #包括 使用名称空间std; 类向量{ 公众: 整数大小; int*a; 向量(int n,int val); ~vectmy(){delete[]a;//如果我删除了这个程序,它就会工作 } 向量和运算符=(常量向量和); }; vectmy::vectmy(int n,int val){ 尺寸=n; a=新整数[n+1]; 对于(int i=0;i,c++,class,destructor,C++,Class,Destructor,在操作符中+您可以 vectmy result = left; 这将调用默认构造函数和复制构造函数,其中您没有。因此将使用编译器变量,它不会为a成员分配内存。对于自动生成的复制构造函数,指针将被简单复制,使两个对象使用同一指针。当一个对象删除它时,另一个对象将使用另一个指针急诊室无效 你应该读一下 当我运行它时,它崩溃了。如果我移除析构函数,它就会工作。为什么会发生这种情况 您的操作员+在此处创建左侧的副本: vectmy result = left; 由于没有显式定义复制构造函数,编译器将

操作符中+
您可以

vectmy result = left;
这将调用默认构造函数和复制构造函数,其中您没有。因此将使用编译器变量,它不会为
a
成员分配内存。对于自动生成的复制构造函数,指针将被简单复制,使两个对象使用同一指针。当一个对象删除它时,另一个对象将使用另一个指针急诊室无效

你应该读一下

当我运行它时,它崩溃了。如果我移除析构函数,它就会工作。为什么会发生这种情况

您的
操作员+
在此处创建
左侧的副本

vectmy result = left;
由于没有显式定义复制构造函数,编译器将隐式生成一个执行成员复制的构造函数

A
数据成员的单调副本意味着
A
指针最终将指向两个不同的
vectmy
result
left
)实例的相同位置,这两个
指针在销毁时将
删除[]

这样的双重删除会使您的程序出现未定义的行为,在您的情况下,这种行为表现为崩溃

这就是问题的关键:每当您有一个用户定义的复制构造函数、赋值运算符或析构函数时,您可能都应该定义它们中的所有

原因是您通常会定义其中一个函数,因为您正在管理某些资源(在您的情况下是内存),并且在复制、销毁或分配管理资源的对象时,您通常希望执行正确的操作

在这种特殊情况下,缺少正确的副本构造函数。您可以这样定义它:

vectmy::vectmy(vectmy const& v)
{
    size=v.size;
    a = new int[size];
    *this = v;
}

此外,我建议您可以通过原始指针、<代码>新< /代码>和<代码>删除> /代码>(或它们的数组对应)避免手动内存管理,只要您可以,并考虑使用。

更新:

还要注意,您的
运算符+
正在按值接受其参数,这意味着将复制每个参数(即,将调用复制构造函数)

由于此处实际上不需要复制,您可能希望通过引用获取参数(到
const
):


按照。你需要一个复制构造函数。非常感谢你!我当然会使用std::vector,这只是一个测试,看看带有指针数据成员的类是如何运行的。但是我尝试使用这个操作符:
vectmy vectmy::operator+(const vectmy param){vectmy temp(3,0);例如(int i=0;i@TommasoFerrari:很高兴它有帮助:)原因是您的
运算符+
接受其参数按值传递参数时,将创建一个副本-这意味着将调用副本构造函数。这就是为什么只有在定义正确的副本构造函数时,副本构造函数才起作用。但是,您不需要在此处按值接受参数-您不需要
操作符+
的参数副本。我稍微扩展了我的答案。@托马索费拉里:不客气,祝你的项目好运;)
vectmy operator + ( vectmy const& left, vectmy const& right)
//                         ^^^^^^              ^^^^^^