代码可以工作,但在析构函数中崩溃(没有复制构造函数)

code works but crashes in destructor (without copy constructor)

本文关键字:崩溃 复制 构造函数 析构函数 工作 代码      更新时间:2023-10-16

基本上,我在做作业,我有一个链表,有多项式系数和指数。当没有包含copy c-tor时,代码在退出main(析构函数)时崩溃。对于copy c-tor,它不会发生,但我想知道为什么,因为我没有在任何地方显式地调用copy c-tor。这只是代码的一部分。Coef函数在列表中添加带有参数exp和Coef的节点,因此我认为不需要包含它。

CPList :: ~CPList ()
{
    while (!isEmpty())
        deleteFromHead();
}
void CPList :: deleteFromHead ()
{
    CPNode* tmp=head;
    if (head==tail)
        head=tail=NULL;
    else head=head->next;
    delete tmp;
}
CPList* CPList :: mul (CPList p1, CPList p2)
{
    CPList* res = new CPList;
    CPNode *first, *second;
    for (first=p1.head; first!=NULL; first=first->next)
        for (second=p2.head; second!=NULL; second=second->next)
            res->coef(first->exp+second->exp, first->coef*second->coef);
    res->check();
    return res;
}

它在这段代码之后,在右括号处崩溃。

int main ()
{
...
    ptr=p3.mul(p1, p2);
    ptr->printall();
}

当包含copy c-tor时正常工作

p1p2按值传递给mul,因此创建副本并在mul返回时销毁。

CPList* CPList :: mul (CPList p1, CPList p2) {//code}

当您按值传递并且没有实现默认复制构造函数时-创建对象的浅复制(这意味着简单地复制成员的所有值)
对于simple(内置类型),
但是,如果类中有成员,比如指针或引用&*,那么它们的值就会被复制,这就不好了,因为:
例如:

class A
{
A(){new m_pOnInt};
~A(){delete m_pOnInt};
int* m_pOnInt;
}
void someFunction(A objA);

当你调用someFunction(objA) -提供的A实例的临时副本被创建并压入堆栈,
在函数将控制权返回给调用者后,对堆栈中的所有对象调用函数析构函数,因此调用~objA();但是你仍然有一个类A的实例,它作为someFunction的参数提供,但是用无效的m_pOnInt作为删除操作符应用于它,所以当A的实例的析构函数被称为

时,你会遇到问题

解决方案使用"rule of 3":这意味着当你处理复杂的对象(包含像指针/引用这样的成员)时,实现特殊的成员函数:复制构造函数,赋值操作符,构造函数,这允许你执行深度复制。