尽管遵守规则,但内存泄漏在哪里?

Where is the memory leak despite following the rules?

嘿,我似乎找不到内存泄漏,即使我在初始化对象数组之前删除了所有内容,并在我不再使用它时将其删除。不幸的是,valgrind 没有告诉我错误在哪里,但它确实说我有 10/11 内存泄漏,下面是我的代码。不要中间复制功能的重复性,我会尽快更改它。

// Default Constructor
Basket::Basket() {
  setEmpty();
}

// SetEmpty
void Basket::setEmpty() {
  m_fruits = nullptr;
  m_cnt = 0;
  m_price = 0;
}

// Destructor
Basket::~Basket() {
  delete[] m_fruits;
  m_fruits = nullptr;
}


// copy assignment operator
Basket & Basket::operator = (const Basket & other) {
  if (this != & other) {
    setEmpty();
    m_cnt = other.m_cnt;
    m_price = other.m_price;
    m_fruits = new Fruit[other.m_cnt];
    for (int i = 0; i < other.m_cnt; i++) {
      m_fruits[i] = other.m_fruits[i];
    }
    delete[] other.m_fruits;
  }
  return *this;
}

//set price;
void Basket::setPrice(double price) {
  m_price = price;
}

这里如果m_fruits不为空怎么办?我认为这是一个泄漏。

// SetEmpty
void Basket::setEmpty() {
  m_fruits = nullptr;
  m_cnt = 0;
  m_price = 0;
}

如果您执行以下操作,您就会漏水:

#include "basket.h"

#include <vector>
#include <iostream>

int main(int, char **)
{
    Fruit fruits[2] = {{"Fruit a2"}, {"Fruit b2"}};
    Basket basket2(fruits, 2, 10.0);

    Fruit a("Fruit a");
    Fruit b("Fruit b");
    Basket basket;
    basket +=a;
    basket +=b;

    basket = basket2; // errors happen here
}

您在删除前将 Basket::m_fruits 设置为 nullptr。您需要将 Basket::operator = (const Basket & other) 更改为:

Basket & Basket::operator = (const Basket & other) {
  if (this != & other) {
    if(m_fruits != nullptr) delete[] m_fruits;
    setEmpty();
    m_cnt = other.m_cnt;
    m_price = other.m_price;
    m_fruits = new Fruit[other.m_cnt];
    for (int i = 0; i < other.m_cnt; i++) {
      m_fruits[i] = other.m_fruits[i];
    }
  }
  return *this;
}

如果 m_fruits 仍然是空的,您的 Basket::~Basket() 中的 free/delete 也可能无效。将其更改为:

Basket::~Basket() {
  if(m_fruits != nullptr) delete[] m_fruits;
}

现在以下工作没有问题:

#include "basket.h"

#include <vector>
#include <iostream>

int main(int, char **)
{
    Fruit fruits[2] = {{"Fruit a2"}, {"Fruit b2"}};
    Basket basket2(fruits, 2, 10.0);

    Fruit a("Fruit a");
    Fruit b("Fruit b");
    Basket basket;
    basket +=a;
    basket +=b;

    basket = basket2;
    Basket basket3(basket2);
}