导致 SegFault C++ 的析构函数

Destructor causing SegFault C++

class Pair {

public:

    int *pa,*pb;


    Pair(int a, int b) 
    {
        pa = new int(a);
        pb = new int(b);
    }

    Pair(const Pair& other) {
        int* pc = new int(*other.pa);
        int* pd = new int(*other.pb);
    }


    ~Pair() {
        delete pa;
        delete pb;
    }

};

在这个程序中,编译器产生了一个分段错误(核心转储),在完全删除析构函数后,我们能否将程序运行到 运行 而没有任何错误,所以任何人都可以帮我解决这个问题吗? 即使在参数化构造函数中我初始化了指针,编译器也会警告点 pa 和 pb 未初始化。

对于您的复制构造函数,您应该(很可能)这样做:

Pair(const Pair& other) {
    pa = new int(*other.pa);
    pb = new int(*other.pb);
}

这完成了您希望复制构造函数完成的工作。

使用您的代码,当您在通过其复制构造函数创建的Pair对象上调用析构函数时,您正在尝试删除未初始化的指针。

:你的复制构造函数正在创建两个指针,然后将它们泄露出去。它从不设置 class.

的成员变量

您可能想参考三/五等规则,为了清楚起见,delete 默认构造函数不会有什么坏处。

class Pair {
public:
    int *pa, *pb;

    Pair() = delete;
    Pair(int a, int b): pa{new int{a}}, pb{new int{b}} {}
    Pair(const Pair& other): pa{new int{*other.pa}}, pb{new int{*other.pb} {}

    ~Pair(){
        delete pa;
        delete pb;
    }
};

可能的问题(尽管仅用您当前提供的代码很难判断)是这些行:

int* pc = new int(*other.pa);
int* pd = new int(*other.pb);

这重新声明了新指针 pcpd,并没有实际设置您的成员变量 papb。一旦构造函数退出,这些新指针就会超出范围。在最好的情况下,这是潜在的内存泄漏,在最坏的情况下,您正在 deleteing 未初始化的指针——这可能会导致您的崩溃。

要修复,您需要实际设置您的成员并删除 int* 关键字:

pa = new int(*other.pa);
pb = new int(*other.pb);

不要使用原始指针,而是考虑使用 std::unique_ptr 进行资源管理:

#include <memory>

class Pair {
public:
    std::unique_ptr<int> pa, pb;

    Pair(int a, int b) 
    {
        pa = std::make_unique<int>(a);
        pb = std::make_unique<int>(b);
    }
};

int main() {
    Pair p {1, 2};
    return 0;
}