【发布时间】:2021-03-22 17:37:40
【问题描述】:
我最近正在编写一个 SRPT 程序。我需要使用向量并使用make_heap将向量转换为堆。
但是,我在一个特定的测试用例 int LB = estimateLB({{2, 2}, {2, 6}}, 2);
我在两台机器上测试了代码: Ubuntu会导致这个错误,macOS会正确编译。这真的很奇怪。 错误:
简单的estimateLB函数:
int estimateLB(vector<pair<int, int>> proc, int n) {
int diff = 0;
int i = 1;
// 1. cause error
vector<int> heap;
heap.push_back(proc[0].first);
make_heap(heap.begin(), heap.end(), greater<>{});
// 2. works
// vector<int> *heap = new vector<int>();
// heap->push_back(proc[0].first);
// make_heap(heap->begin(), heap->end(), greater<>{});
// memory access problem
diff = proc[i].second - proc[i - 1].second;
while (diff > 0) {
int temp = heap.front();
if (diff >= temp) {
pop_heap(heap.begin(), heap.end(), greater<>{});
heap.pop_back();
diff -= temp;
}
}
heap.push_back(proc[i].first);
push_heap(heap.begin(), heap.end(), greater<>{});
return 0;
}
如果我使用指针初始化向量,错误似乎已修复。目前,我只知道这两种方式会在不同的位置(堆栈或空闲存储)分配内存。这种机制会导致这个错误吗?有什么想法吗?
提前致谢。
【问题讨论】:
-
您可能会重复从仅包含 single 元素的堆中弹出元素。
-
这不是编译错误,而是代码中的未定义行为。
-
heap.push_back(proc[0].first);-- 如果proc为空怎么办? 如果我使用指针初始化向量,错误似乎已修复。 -- 没有修复 -- 您所做的只是将损坏错误移到其他地方。 -
在 1. 中,您将堆对象放在堆栈框架中,在 2. 中,您将其放在堆中。 “2.works”建议您滥用运行时在违反堆栈帧时检测到但在堆上发生时未被检测到的堆对象?检查 proc[0] 是否是有效调用?也就是说,您提供一个带有所需元素的过程。祝你好运:)
-
仅供参考——这个程序在 Visual Studio 中崩溃了,就在 @KonradRudolph 所说的地方。这是一个逻辑错误的例子,与声明指针和调用
new完全无关。
标签: c++ memory vector memory-leaks