这是蒟蒻芦苇的蓝桥杯国赛赛前题解,也是第6篇题解
题目背景
若某个家族人员过于庞大,要判断两个是否是亲戚,确实还很不容易,现在给出某个亲戚关系图,求任意给出的两个人是否具有亲戚关系。
题目描述
规定:x和y是亲戚,y和z是亲戚,那么x和z也是亲戚。如果x,y是亲戚,那么x的亲戚都是y的亲戚,y的亲戚也都是x的亲戚。
输入格式
第一行:三个整数n,m,p,(n<=5000,m<=5000,p<=5000),分别表示有n个人,m个亲戚关系,询问p对亲戚关系。
以下m行:每行两个数Mi,Mj,1<=Mi,Mj<=N,表示Mi和Mj具有亲戚关系。
接下来p行:每行两个数Pi,Pj,询问Pi和Pj是否具有亲戚关系。
输出格式
P行,每行一个’Yes’或’No’。表示第i个询问的答案为“具有”或“不具有”亲戚关系。
----------------------分割线----------------
正文开始:
这是一个很好的并查集板子题,蓝桥赛前的我怕考到并查集,就决定来练一下,顺便写一篇题解
思路:纯并查集,定义查询函数,然后分组就OK了
代码区:
#include<bits/stdc++.h>
using namespace std;
int n,m,p,a1,a2,f[100005];//定义杂七杂八的东西
int find(int r){//定义一个查询函数,和找祖宗差不多
if(f[r]!=r) f[r]=find(f[r]);//他自己不是自己的爸爸,说明他还有爸爸(祖宗),那就继续找
return f[r];//说明他自己就是自己的祖宗,归入
}//这个地方有点绕,大家可以稍加思考一下
int main(){
cin>>n>>m>>p;
for(int i=1; i<=n; i++){//预处理一下,给他们安排好“房间”
f[i]=i;
}
for(int i=1; i<=m; i++){//读入,并归入自己的房间,将是亲戚的都分到一个房间里去
cin>>a1>>a2;
f[find(a1)]=find(a2);
}
for(int i=1; i<=p; i++){
cin>>a1>>a2;//输入两个人
if(find(a1)==find(a2)) puts("Yes");//如果是一个房间的,那么就是亲戚
else puts("No");//否则就不是
}
return 0;
}
总的来说,这道题目还是比较好做的,我的板子喜欢的也可以收藏一下哦~
在这里,芦苇也祝参加蓝桥杯的大佬们rp++!
rp += oo【手滑动稽】
rp += oo【手滑动稽】