【问题标题】:C++ Trouble deleting dynamic sized array of pairs [closed]C ++麻烦删除动态大小的对数组[关闭]
【发布时间】:2017-09-19 20:51:58
【问题描述】:

我在删除 m_Array 时遇到很多问题。程序在执行清理部分时会在最后出现段错误。我在 m_Array 中有两个具有不同数据的 A 类对象,并且在程序中的某个时刻,来自一个对象的数据开始“环绕”到另一个数组中,从而导致数据不正确。 T 代表我的模板化数据类型。

还有一个B类,它只是创建了两个A类对象

在类声明 A 中公开声明如下:

template <typename T> class A
{
public:
    pair<T, int> *m_Array;  // Array of type pair
    A(int size=1);       // constructor
    ~A();     // A destructor

    // ... all other definitions //

 };

在类 A 的构造函数定义中定义如下:

template <typename T>
A<T>::A(int size) {

    // Set array size
    m_Array = new pair<T, int>[size];

    // Initialize values
    for (int i = 0; i < size; i++) {
        m_Array[i] = make_pair(-1, -1);
    }

    //... other things defined and initialized...//
}

在 A 类的析构函数中:

template <typename T>
A<T>::~A() {

        delete [] m_Array; // Not working as it should
}

重载赋值运算符

template <typename T>
const A<T>& A<T>::operator=(const A<T>& rhs) {
    m_AArraySize = rhs.m_AArraySize;
    m_currASize = rhs.m_currASize;

    for (int i = 0; i < m_currASize; i++) {

        m_Array[i].first = rhs.m_Array[i].first;
        m_Array[i].second = rhs.m_Array[i].second;
    }

    _ptr = rhs._ptr;

    return *this;
}

复制构造函数

template <typename T>
A<T>::A(const A<T>& other) {
    m_AArraySize = other.m_AArraySize;
    m_AHeapSize = other.m_AHeapSize;

    for (int i = 0; i < m_currASize; i++) {
        m_Array[i].first = other.m_Array[i].first;
        m_Array[i].second = other.m_Array[i].second;
    }

    _ptr = other._ptr;
}

B 类声明

template <typename T> class B{
public:
    //B constructor
    B(int size);


    int m_currBSize;        // spots used in array
    int m_BSize;            // size of array

    A <T> oneAHolder;
    A <T> twoAHolder;

};

B 类构造函数

template <typename T>
b<T>::b(int size){
    A<T>(size);

    m_BArraySize = size;
    m_currBSize = 1;

    // Create two A objects
    A<T> oneA(size);
    A<T> twoA(size);

    // oneA and twoA go out of scope
    oneAHolder = oneA;
    twoAHolder = twoA;
}

在我的主要功能中,我正在创建一个 B 类对象,并使用它的插入函数将数据插入到它的两个 A 对象中。

我尝试了几种不同的方法从数组中删除数据,并阻止数据溢出到另一个数组中,但无济于事。

感谢您的帮助!

P.S.:请不要“只使用 std::vector”

编辑:添加了更多我的代码

【问题讨论】:

  • 你所说的“环绕”是什么意思?对我来说,这听起来更像是一个双重免费问题。您是在使用复制 ctor 还是将一个对象 A 分配给另一个 A newA = anotherA?看看这个stackoverflow.com/questions/7823845/… 或实现这些功能。
  • 向我们展示您的main 程序。根据您发布的内容,只需两行代码即可轻松破解程序。
  • "只需使用 std::unique_ptr"
  • 顺便说一句,您似乎忘记实现移动/复制构造函数。这是故意的吗?
  • 上面的代码中有A类的拷贝构造函数和重载赋值运算符。

标签: c++ arrays destructor delete-operator


【解决方案1】:

鉴于您发布的代码,您的赋值运算符有两个问题:

1) 赋值运算符泄漏内存,因为您未能释放旧内存。

2) 除非this-&gt;m_Array 已经足够大,否则您将覆盖for 循环中的内存,因为this-&gt;m_Array 是比rhs.m_Array 更小的缓冲区。

您可以简单地使用copy/swap idiom,而不是所有这些错误代码。

#include <algorithm>
//...
template <typename T>
A<T>& A<T>::operator=(const A<T>& rhs) 
{
    A<T> temp(rhs);
    std::swap(temp.m_AArraySize, m_AArraySize);
    std::swap(temp.m_currASize, m_currASize);
    std::swap(temp.m_Array, m_Array);
    std::swap(temp._ptr, _ptr);
    return *this;
}

如果您编写了不间接调用赋值运算符的 正确 复制构造函数和 正确 析构函数,则此方法有效。如果其中任何一个功能出现故障,上述方法将不起作用。

假设复制构造函数和析构函数没有错误,以这种方式编写赋值运算符可以避免重写复制构造函数的代码,因为您只是重用它。

如果A 中有更多您未在帖子中指定的成员变量,它们也都需要交换。

简而言之,这基本上只是复制rhs 并将this 中的所有旧数据与temp 交换。然后temp 以旧数据结束。

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 2013-02-11
    • 1970-01-01
    • 2017-10-13
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多