题目中的三个实际上都是同一个概念。
如果仅仅是想象成二叉树去处理,并且是从上往下插入。会遇到很多很蛋疼的问题。
然后伟大的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;
}