递归传递动态变量的内存泄漏
Posted
技术标签:
【中文标题】递归传递动态变量的内存泄漏【英文标题】:Memory leaks passing dynamic variables recursively 【发布时间】:2014-01-28 09:15:54 【问题描述】:我有一个递归函数,每次调用该函数时都需要创建一个新数组。该函数还需要之前创建的数组:
void myFunc(int* prevArray)
int newSize;
//do some calculations to find newSize
int* newArray;
newArray = new int[newSize];
//do some calculations to fill newArray
//check some stopping condition
myFunc(newArray);
这个函数会泄漏内存,但我无法通过添加来避免这种情况
删除[] newArray;
因为我只能在再次调用该函数后添加它。我该如何解决这个问题?
【问题讨论】:
在调用myFunc
之后做delete[] newArray;
有什么问题?
好吧,只要递归继续进行,它就会一直堆积内存。数组相当大,我需要经常调用这个函数。
你可以删除prevArray
,除非它等于nullptr。
@RobVerheyen 好吧,这似乎是您算法的自然结果 - 每次连续调用 myFunc
都需要一个由前一次调用计算的大数组。
不会从前一个实例中复制 prevArray 吗?
【参考方案1】:
您可以通过使用动态内存分配来解决这个问题。
// allocate initial size
const int INITIAL_SIZE = 5;
int *myArray = malloc(sizeof(int) * INITIAL_SIZE));
int myFunc(int *aArray, int numAllocated)
int numElements = calculateNewSize();
if (numElements != numAllocated)
// allocate new size
realloc(aArray, (numElements * sizeof(int));
return numElements;
现在您可以像这样调用 myFunc:
int numElements;
numElements = myFunc(myArray, numElements);
使用完 myFunc 后,别忘了释放内存
free(myArray);
【讨论】:
这似乎是一个很好的解决方案,但问题是 newArray 的内容取决于 prevArray 的内容。我知道 realloc 保留了旧内存块中的所有内容,但我的 newArray 不仅仅是我的旧数组,最后添加了一些东西。它们表示在它们之间完成了一些线性代数的矩阵。 我没看出问题,那你为什么不初始化数组呢?元素的数量是给定的变量,因此很容易编写一个初始化函数来迭代所有元素。【参考方案2】:试试类似的东西
void myFunc(int* prevArray)
int newSize;
...newArray = new int[newSize];
myFunc(newArray);
delete[] newArray;
或者更好的是使用 std::unique_ptr 来控制 newArray 内存。通过这种方式,您将遵循有关动态内存的经验法则 - 它应该有一个所有者,负责分配和释放它。
【讨论】:
【参考方案3】:您可能只是使用向量并将新结果交换为最终结果。
#include <iostream>
#include <vector>
struct X ~X() std::cout << "Destruction\n"; ;
void recursive(unsigned n, std::vector<X>& result)
// Put new_result in a scope for destruction
std::vector<X> new_result(1);
// Do something
// The previous result is no longer needed
std::swap(result, new_result);
// Next recursion
if(n)
std::cout << "Call\n";
recursive(--n, result);
int main()
std::vector<X> result(1);
std::cout << "Call\n";
recursive(3, result);
return 0;
【讨论】:
我不完全确定我是否理解您的意思。结构是否意味着包含我的数组? 不,它的目的只是为了显示删除点 - std::vector以上是关于递归传递动态变量的内存泄漏的主要内容,如果未能解决你的问题,请参考以下文章