【发布时间】:2014-08-29 04:07:52
【问题描述】:
我一直在尝试实现 Heap 数据类型,但我碰壁了。
由于很多以前的答案都要求提供 moar 代码,所以这里是:
#include <iostream>
#include <vector>
#include <iomanip>
using namespace std;
template <typename T> void display_array(vector<T> arr, bool endline = true)
{
cout << arr.size() << endl;
for (int i = 0; i < arr.size() - 1; i++) cout << arr[i] << ", ";
cout << arr[arr.size() - 1];
if(endline) cout << endl;
}
template <class T> class Heap
{
//typedef T Node;
// setw(...);
//private:
public:
vector<T>* elems;
Heap() : elems(nullptr)
{
this->elems = new vector<T>;
}
Heap(vector<T> e)
{
this->elems = new vector<T>(e);
}
Heap(vector<T>* e)
{
this->elems = e;
}
Heap(Heap<T>& h)
{
this->elems = new vector<T>(h.elems);
}
~Heap()
{
delete elems;
}
T elemAt (int index)
{
return (*(this->getElems())) [index];
}
vector<T>* getElems()
{
return this->elems;
}
int parent (int index)
{
return index / 2;
}
long getSize()
{
return this->getElems()->size();
}
int left (int index)
{
return 2 * index;
}
T leftElem (int index)
{
return this->elems [2 * index];
}
int right (int index)
{
return 1 + 2 * index;
}
T rightElem (int index)
{
return this->elems [1 + 2 * index];
}
bool withinHeap (int index)
{
return index <= (this->getSize());
}
void maxHeapify(int index)
{
int largest = index;
int l = left(index);
int r = right(index);
if (withinHeap(l) && elemAt(l) > elemAt(index))
{
if (withinHeap(r) && elemAt(r) > elemAt(l))
{
largest = r;
}
largest = l;
}
if (largest != index)
{
int temp = elemAt(index);
elemAt(index) = elemAt(largest);
elemAt(largest) = temp;
delete temp;
}
/* or return withinHeap(l) && elemAt(l) > elemAt(index) ? withinHeap(r) && elemAt(r) > elemAt(l) ? r : l : index; :) */
}
void display(int current, int indent)
{
if(withinHeap(left(current))) display(left(current), indent + 4);
if (indent > 0) cout << setw(indent) << " ";
cout << elemAt(current) << endl;
if(withinHeap(right(current))) display(right(current), indent + 4);
}
};
int main()
{
vector<int> vec {2, 5, 4, 12, 3, 9};
Heap<int>* h = new Heap<int>(vec);
display_array(*h->getElems());
h->display(0, 0);
return 0;
}
最后一条语句 (h->display(0,0)) 会导致段错误。我已将其范围缩小到 getSize() 函数。
在 gdb 中,print this.elems 和 print *this.elems 没问题(它们返回对象跟踪或它们所称的任何内容),但是当我键入 print *this.elems->size() gdb 时会回复
Cannot access memory at address 0xbf7fffef
我对 C++ 和 gdb 以及所有东西都很陌生。这里有什么问题?
【问题讨论】:
-
仅供参考,您的
Heap课程可以使用 3 行 main() 程序来破解。都是因为缺少用户定义的赋值运算符.. -
你真的不需要/想要一个指向
vector的指针。 -
问题不在于您的 getSize() 函数,而在于您的算法。我在 getSize() 中放了一条 cout 语句,我的终端被垃圾邮件发送了。我的猜测是,由于递归函数存在缺陷,您会遇到 Stack Overflow。
-
您的代码看起来更像 Java 和 C# 而不是 C++。你为什么在那里做那个 new Heap
?你不能直接创建对象吗?如果为它分配动态内存,则应在使用后删除 Heap。 C++ 没有垃圾收集器。 -
@SohamChowdhury 您在 main() 函数中有泄漏。我还可以通过将一个
Heap对象简单地分配给另一个对象来创建一个。Heap h1; Heap h2; h2 = h1;不仅会泄漏,还会在同一个指针上调用delete两次,导致未定义的行为,可能会崩溃。鉴于简单的 3 行程序会造成这种破坏,希望它表明这并不像您想象的那么简单或直观。