题目描述
又到了一年圣诞节,圣诞老人拿出手机一看朋友圈,发现很多人都想要一顶圣诞帽子,于是圣诞老人很开心的带着一群驯鹿去市场买圣诞帽子,但是他很快就发现了一个问题:每个人都想要一顶不和朋友重复的圣诞帽,否则他就会不开心。比如A认识B,B认识C,那么A肯定也认识C,所以ABC 的帽子都不能有相同的一顶。
这可把圣诞老人难坏了,好在市场有很多种类的圣诞帽子(可以看作无限多),请你告诉他最少需要买多少种?
输入格式
输入一共有两行,第一行N表示有N种朋友关系,第二行一共有N组数p和q,表示p和q相互认识。
输出格式
输出一个数表示一共需要买多少种帽子圣诞帽子
样例输入
1 1 2
样例输出
2
提示
0< N,p,q<= 100
这个题最关键的思路在于标红部分,对于标红部分以外的来说就是并查集的简单模型,而处理标红部分则是这道题的关键,因为只是在认识的人(才需要不同种类的帽子),而在输入的朋友关系所构成的线路上,每一条朋友线路都可以看成互相平行得,我们只需要找出最长的那条线路即可
这道题的解题思路为记录每一条朋友线路上的个数,然后找出朋友个数最多的输出其余的和最基本的并查集并无两样
#include <iostream>
#include <stdio.h>
using namespace std;
int fa[10010];
int sz[10010];//每个帽子的
int find(int x)
{
if(fa[x]==x)
{
return x;
}
else
{
return fa[x]=find(fa[x]);
}
}
void check(int a,int b)
{
a=find(a);
b=find(b);
if(a!=b)
{
fa[a]=b;
sz[b]+=sz[a];//将其该组累计于下一位 (父亲的身上)相当于该条朋友线上需要帽子的种类+1
sz[a]=0;//该(儿子)完成了复制任务后就结束变为0 //即使不将其变为0其实也行QvQ
}
}
int main()
{
int n;
cin>>n;
for(int i=1;i<=101;i++)
{
fa[i]=i;//对集合进行初始化
sz[i]=1;//至少一种帽子所以将所有初始化为1
}
for(int i=1;i<=n;i++)
{
int a,b;
cin>>a>>b;
check(a,b);
}
int ans=0;
for(int i=1;i<=100;i++)//从一开始遍历寻找最多种类的,最多种类的就是答案
{
ans=max(ans,sz[i]);
}
cout<<ans<<endl;
return 0;
}