HDU 1512 Monkey King(左偏树+并查集)
来源:互联网 发布:spss数据分析书推荐 编辑:程序博客网 时间:2024/06/05 18:03
题目链接:Click here
题意:有n个猴子,一开始每个猴子只认识自己。每个猴子有一个能力值,能力值越大表示这个猴子越厉害。如果2个猴子不认识,他们就会找他们认识的猴子中能力最强的出来决斗,决斗的2个猴子力量值减半,然后这2拨猴子就都认识了,不打不相识嘛。现在给m组询问,如果2只猴子相互认识,输出-1,否则他们各自找自己认识的最厉害的猴子单挑,求决斗完后这拨猴子力量最大值。
思路:两拨不认识得猴子决斗后认识,涉及到合并,于是想到并查集。又要求两拨猴子的最强战斗力,大顶堆比较合适,而堆得合并,用到了刚看到的左偏树。
左偏树:(引用百度百科) [性质1] 节点的键值小于或等于它的左右子节点的键值。 [性质2] 节点的左子节点的距离不小于右子节点的距离。 [性质3] 节点的距离等于它的右子节点的距离加1。 我们的印象中,平衡树是具有非常小的深度的,这也意味着到达任何一个节点所经过的边数很少。左偏树并不是为了快速访问所有的节点而设计的,它的目的是快速访问最小节点以及在对树修改后快速的恢复堆性质。从图中我们可以看到它并不平衡,由于性质2的缘故,它的结构偏向左侧,不过距离的概念和树的深度并不同,左偏树并不意味着左子树的节点数或是深度一定大于右子树。
代码:
#include <iostream>#include <cstring>#include <cstdio>#include <queue>#include <cstdlib>using namespace std;int father[100005];struct Monkey{ int left, right; int dis; int blood;} LTree[100005];int findx(int x){ if(x == father[x])return x; return father[x] = findx(father[x]);}int merges(int x,int y){ int left, right; if( x == 0 ) return y; if( y == 0) return x; if( LTree[x].blood < LTree[y].blood) //大顶堆 swap(x,y); LTree[x].right = merges(LTree[x].right,y); left = LTree[x].left; right = LTree[x].right; father[right] = x; //修改并查集的根 if(LTree[left].dis < LTree[right].dis) swap(LTree[x].left,LTree[x].right); if(LTree[x].right == 0) LTree[x].dis = 0; else LTree[x].dis = LTree[LTree[x].right].dis + 1; return x;}int del(int x){//删除根节点,并合并左右子树 int left, right; left = LTree[x].left; right = LTree[x].right; father[left] = left; father[right] = right; LTree[x].left = LTree[x].right = LTree[x].dis = 0; return merges(left, right);}void fight(int a,int b){//两棵树根节点血量减半,并与子树再次合并 int left,right; LTree[a].blood /= 2; LTree[b].blood /= 2; left = del(a); right = del(b); left = merges(left, a); right = merges(right, b); left = merges(left,right); printf("%d\n",LTree[left].blood);}int main(){ int n, m, x, y, a, b; while(scanf("%d",&n) != EOF) { for(int i = 1; i <= n; i++) { scanf("%d",<ree[i].blood); LTree[i].left = 0; LTree[i].right = 0; LTree[i].dis = 0; father[i] = i; } scanf("%d",&m); for(int i = 1; i <= m; i++) { scanf("%d%d",&x,&y); a = findx(x); b = findx(y); if(a == b) printf("-1\n"); else fight(a, b); } } return 0;}
0 0
- HDU 1512 Monkey King(左偏树+并查集)
- HDU 1512 Monkey King(左偏树+并查集)
- Hdu 1512 Monkey King(左偏树+并查集)
- HDU ACM 1512 Monkey King->左偏树+并查集
- hdu-1512 Monkey King [并查集+左偏树]
- HDU 1512 Monkey King 左偏树 + 并查集
- HDU 1512 Monkey King 并查集+左偏树
- |Hdu 1512|可并堆|并查集|Monkey King
- hdu 1512 Monkey King (左偏树可并堆 并查集)
- 【左偏树+并查集】Monkey King HDU1512
- ZOJ2334 Monkey King 左偏树+并查集
- hdu1512-Monkey King- 左偏树+并查集
- 左偏树+并查集 hdu1512 Monkey King
- HDU1512 Monkey King【并查集+左偏树】
- hdu 1512 Monkey King (左偏树 可并堆)
- hdu 1512 Monkey King 左偏树(可并堆)
- zoj2334 Monkey King , 并查集,可并堆,左偏树
- zoj 2334 Monkey King(左偏树+并查集)
- 读书笔记MoreEffectiveC++(20)
- CListCtrl的主要事件及鼠标响应函数
- js 简单计算器
- 字符串训练 ----------- uva 10361 Automatic Poetry
- Hadoop启动时报错:Incorrect configuration: namenode address dfs.namenode.servicerpc-address or...
- HDU 1512 Monkey King(左偏树+并查集)
- 来自大数据的反思:需要你读懂的10个小故事 三
- Response.End导致“正在中止线程”异常的问题
- HDU 1024 Max Sum Plus Plus(DP,)
- 3518e_ov9750
- 【实例】HTML5中video播放视频实现特效
- xcode插件存放路径
- jQuery on()方法 jQuery删除节点的三个方法:remove empty detach
- android 字符串比较