【模板】小根堆模板

小根堆的两种写法

手写堆

可以视作是一种完全二叉树结构

#include<iostream>
#include<cstring>
#include<algorithm>
#include<cstdio>
using namespace std;
const int Maxn=1000005;
int sta[Maxn];
int n,tot=0;//tot记录元素总数,记得及时更新
inline int read() {
	int x=0,w=1;
	char ch=0;
	while(ch!='-' && (ch<'0' || ch>'9')) ch=getchar();
	if(ch=='-') w=-1,ch=getchar();
	while(ch>='0' && ch<='9') x=x*10+ch-'0',ch=getchar();
	return x*w;
}
inline void push(int b) {
	sta[++tot]=b;
	for(int i=tot,j=i>>1; j; i=j,j=i>>1) {
		if(sta[j]>sta[i]) swap(sta[j],sta[i]);
		//只需要判断当前节点与父亲的大小关系
	}
}
inline void pop() {
	sta[1]=sta[tot--];//最小值覆盖掉
	for(int i=1,j=i<<1; j<=tot; i=j,j=i<<1) {
		if(j+1<=tot&&sta[j+1]<sta[j]) j++;//因为是小根堆,所以在两个兄弟节点之间选取更小的那个向上推
		if(sta[i]<sta[j]) break;//此时没有交换的必要
		else swap(sta[i],sta[j]);

	}
}
int main() {
	n=read();
	int a,b;
	for(int i=1; i<=n; i++) {
		a=read();
		if(a==1) {
			b=read();
			push(b);
		} else if(a==2) printf("%d\n",sta[1]);
		else if(a==3) pop();
	}
	return 0;
}

STL

可以用优先队列

#include<iostream>
#include<cstdio>
#include<cstring>
#include<string>
#include<algorithm>
#include<queue>
using namespace std;
priority_queue <int> q;//定义堆
int n;
int main()
{
    scanf("%d",&n);
    for(int i=1;i<=n;i++)
    {
        int opt,x;
        scanf("%d",&opt);
        if(opt==1) scanf("%d",&x),q.push(-x);//加负号
        if(opt==2) printf("%d\n",-q.top());//加负号
        if(opt==3) q.pop();
    }
    return 0;
}
posted @ 2019-11-20 19:38  bbqub  阅读(448)  评论(0编辑  收藏  举报