题目中的三个实际上都是同一个概念。

如果仅仅是想象成二叉树去处理,并且是从上往下插入。会遇到很多很蛋疼的问题。

然后伟大的wiki告诉我们。实际上是不是这么 想的。

插入的时候。每次len++,然后插入总是在底部插入。然后遇到不合法的情况,只要和父亲节点交换就可以了。

在删除的时候。然后弄一个数组,记录父亲节点的位置,然后先向上更新,再向下更新。

/*
构建一个大根堆
*/
#include
<iostream>
#include
<algorithm>

using namespace std;
const int N = 10024;
int n;
struct myHEAP{
int len;
int data[N];

void addElem(int t);
int getMaxElem();
}heap;
//插入的时候只需要的父节点比较
void myHEAP::addElem(int t){
if(len == 0){
len
++;
data[
0] = t;
return ;
}
else{
len
++;
int parent = floor((len-1)/2.0);
int son = len;
data[son]
= t;
while(1){
if(data[parent] < data[son]){
swap(data[parent],data[son]);
if(parent == 0)
break;
son
= parent;
parent
= floor((parent - 1)/2.0);
}
else break;
}
}

}
int myHEAP::getMaxElem(){
return data[0];
}
int init(){
if(scanf("%d",&n) == EOF)
return 0;
int t;
memset(
&heap,0,sizeof(heap));
for(int i = 0; i <= n; i++){
scanf(
"%d",&t);
heap.addElem(t);
}
return 1;
}
void work(){
char str[1024];
int gg;
while(1){
gets(str);
if(str[0] == 'g')
cout
<<heap.getMaxElem()<<endl;
else if(str[0] == 'a'){
scanf(
"%d",&gg);
heap.addElem(gg);
}
else continue;
}
}
int main(){
while(init()){
work();
}
return 0;
}

  很挫的代码。

下面是别人的。

#include <algorithm>
#include <cstdio>
using namespace std;
#define size a[0].first
typedef pair<int, int> PII;
const int MAXN = 1000000;
struct binary_heap
{
    int p[MAXN];
    PII a[MAXN];
    inline void up(int i)
    {
        for (; i > 1 && a[i] > a[i >> 1]; i >>= 1)
        {
            swap(a[i], a[i >> 1]);
            swap(p[a[i].second], p[a[i >> 1].second]);
        }
    }
    inline void down(int i)
    {
        for (int j = i << 1; j <= size; i = j, j <<= 1)
        {
            if (j + 1 <= size && a[j + 1] > a[j])
                ++ j;
            if (a[j] > a[i])
            {
                swap(a[i], a[j]);
                swap(p[a[i].second], p[a[j].second]);
            }
            else
                break;
        }
    }
    inline void insert(PII x)
    {
        a[++ size] = x;
        p[a[size].second] = size;
        up(size);
    }
    inline void erase(int i)
    {
        a[i] = a[size --];
        p[a[i].second] = i;
        up(i);
        down(i);
    }
    inline PII get_max()
    {
        return a[1];
    }
} hp1, hp2;
int main()
{
    int t;
    while (scanf("%d", &t) && t)
        if (t == 1)
        {
            int k, p;
            scanf("%d%d", &k, &p);
            hp1.insert(make_pair(p, k));
            hp2.insert(make_pair(-p, k));
        }
        else if ((t == 2 ? hp1.size : hp2.size) == 0)
            puts("0");
        else
        {
            PII ans = t == 2 ? hp1.get_max() : hp2.get_max();
            printf("%d\n", ans.second);
            hp1.erase(hp1.p[ans.second]);
            hp2.erase(hp2.p[ans.second]);
        }
    return 0;
}