构建MaxHeap最大不被发送到顶部

时间:2017-01-22 22:41:12

标签: c++ sorting vector heap

我正在尝试使用大小为10的向量构建最大堆。它包含数字1-10。然而,我的程序不会将最大值10设置为最大变量,因为比较时它超出了我的向量范围。

if ((l <= v.size()) && (v.at(l) > v.at(i)))
    {largest = l;}
    else { largest = i; }

    if ((r <= v.size()) && (v.at(r) > v.at(largest))) // r at some point is 10. which exceeds v.
    {largest = r;}

我尝试围绕上面的代码设置一个if语句来捕获错误,但后来我得到了这个:

INPUT:  1 2 3 4 5 6 7 8 9 10
OUTPUT: 9 8 7 4 5 6 3 2 1 10

这几乎是正确的,但10应该是第一个。我该怎么做才能确保堆正确构建?这是我的完整代码:

#include <iostream>
#include <fstream>
#include <string>
#include <vector>

using namespace std;


vector<string> readFile(string fileName) { /* read in file. Works Fine.*/}
void display(vector<string>& v)  {/*displays vector. works fine. */  }

inline int parent(int i){return i / 2; }
inline int left(int i)  {return 2*i;}
inline int right(int i) {return 2*i + 1;}

void Max_Heapify(vector<string>& v, int i)
{
    int largest;
    int l = left(i);
    int r = right(i);
    i--;

    if ((l <= v.size()) && (v.at(l) > v.at(i)))  
    {largest = l;}
    else { largest = i; }

    if ((r <= v.size()) && (v.at(r) > v.at(largest)))
    {
        largest = r;
    }

    if (largest != i)
    {
        string temp = v.at(i);
        v.at(i) = v.at(largest);
        v.at(largest) = temp;

        Max_Heapify(v, largest);
    }
}

void Build_Max_Heap(vector<string>& v, int length) 
{
    for (int i = (length / 2); i > 0; i--)
    {
        Max_Heapify(v, i);
    }
}

int main() {
    vector<string> vectorReadIn;
    vector<string> sortedVector;
    int x = 0;

    string fileName = "C:/Users/user/Downloads/Algorithims/Perm Words/perm15k.txt";

    vectorReadIn = readFile(fileName);

    cout << "Unsorted file:" << endl;
    display(vectorReadIn);
    vectorReadIn.resize(vectorReadIn.size());
    Build_Max_Heap(vectorReadIn, vectorReadIn.size());

    display(vectorReadIn);  
}

1 个答案:

答案 0 :(得分:0)

除了Igor Tandetnik的评论之外,你对左右孩子的计算是错误的。在索引为0的向量中,堆的根位于索引0.因此左右子的计算为:

left child: (2*x) + 1
right child: (2*x) + 2

您的计算是针对索引为1的根的堆。

此外,Build_Max_Heap函数中的循环必须是:

for (int i = (length / 2); i >= 0; i--)

也就是说,您必须检查矢量中的第一项是否需要重新排列。