您的位置:首页 > 其它

左偏堆

2015-12-29 21:47 274 查看
左偏堆,顾名思义就是向左偏的堆,也就是左边特别重的堆。

左偏堆是一种可并堆,其实现的基本操作是,合并,删除,插入(就是与一个只有一个节点的左偏堆合并)

合并操作

int pop(int a){
int l=heap[a].l;
int r=heap[a].r;
heap[l].f=l;
heap[r].f=r;
heap[a].l=heap[a].r=heap[a].dis=0;
return merge(l,r);
}


删除
以下为例题
http://acm.zju.edu.cn/onlinejudge/showProblem.do?problemCode=2334
#include<cstdio>
#include<algorithm>

using namespace std;

struct tree{
int l,r,v,f,dis;
} heap[100005];

int merge(int a,int b){
if (a==0) return b;
if (b==0) return a;
if (heap[a].v<heap[b].v) swap(a,b);
heap[a].r=merge(heap[a].r,b);
heap[heap[a].r].f=a;
if(heap[heap[a].l].dis<heap[heap[a].r].dis) swap(heap[a].l,heap[a].r);
if(heap[a].r==0) heap[a].dis=0;
else heap[a].dis=heap[heap[a].r].dis+1;
return a;
}

int pop(int a){
int l=heap[a].l;
int r=heap[a].r;
heap[l].f=l;
heap[r].f=r;
heap[a].l=heap[a].r=heap[a].dis=0;
return merge(l,r);
}

int find(int a){
return heap[a].f==a?a:find(heap[a].f);
}

void read(int &x){
char ch;
x=0;
ch=getchar();
while (!(ch>='0'&&ch<='9')) ch=getchar();
while ((ch>='0'&&ch<='9')) {
x=x*10+ch-'0';
ch=getchar();
}
}

int main(){
int i,a,b,finda,findb,n,m;
while (scanf("%d",&n)==1){
for (int i=1;i<=n;i++){
read(heap[i].v);
heap[i].l=heap[i].r=heap[i].dis=0;
heap[i].f=i;
}
read(m);
while(m--){
read(a);read(b);
finda=find(a);
findb=find(b);
if(finda==findb) printf("-1\n");
else{
heap[finda].v/=2;
int u=pop(finda);
u=merge(u,finda);
heap[findb].v/=2;
int v=pop(findb);
v=merge(v,findb);
printf("%d\n",heap[merge(u,v)].v);
}
}
}
return 0;
}


最后是论文
http://wenku.baidu.com/link?url=t55yGX-UkUdEXBhpvBwuzjKP16F7lFl0RKSVVBBW5zXWRB7rRXvLLj1jM-pzhbH834hQl0KKT4va247VmSepsGDSrYF1E3le_WpnKc2xfCi
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: