HDU - 2545 树上战争(没有路径压缩的并查集)

来源:互联网 发布:软件 qa qc区别 编辑:程序博客网 时间:2024/05/16 02:30
树上战争
Time Limit: 4000MS Memory Limit: 32768KB 64bit IO Format: %I64d & %I64u

Submit Status

Description

给一棵树,如果树上的某个节点被某个人占据,则它的所有儿子都被占据,lxh和pfz初始时分别站在两个节点上,谁当前所在的点被另一个人占据,他就输了比赛,问谁能获胜 
 

Input

输入包含多组数据 
每组第一行包含两个数N,M(N,M<=100000),N表示树的节点数,M表示询问数,N=M=0表示输入结束。节点的编号为1到N。 
接下来N-1行,每行2个整数A,B(1<=A,B<=N),表示编号为A的节点是编号为B的节点的父亲 
接下来M行,每行有2个数,表示lxh和pfz的初始位置的编号X,Y(1<=X,Y<=N,X!=Y),lxh总是先移动 

 

Output

对于每次询问,输出一行,输出获胜者的名字
 

Sample Input

2 1 1 2 1 2 5 2 1 2 1 3 3 4 3 5 4 2 4 5 0 0
 

Sample Output

lxh pfz lxh提示:本题输入、输出都很多,请使用scanf和printf代替cin、cout。
 


简单建树,然后查询到根节点需要的步数,步数少的胜


#include<iostream>#include<cstdio>#include<cstring>using namespace std;const int MAXN = 100000 + 100;int parent[MAXN];int n, m;void make_set(){for (int i = 0; i <= n; i++)parent[i] = i;}int find_set(int t){int num = 0;int j = parent[t];int i = t;while (j != i){i = j;j = parent[j];num++;}return num;}void union_set(int a, int b){parent[b] = a;}int main(){while (scanf("%d%d", &n, &m) != EOF && n){int a, b;make_set();for (int i = 0; i < n - 1; i++){scanf("%d%d", &a, &b);union_set(a, b);}for (int i = 0; i < m; i++){scanf("%d%d", &a, &b);int l = find_set(a);int p = find_set(b);if (p<l) printf("pfz\n");else printf("lxh\n");}}}


1 0
原创粉丝点击