题目
题目背景
小明在 A 公司工作,小红在 B 公司工作。
题目描述
这两个公司的员工有一个特点:一个公司的员工都是同性。
A 公司有 NN 名员工,其中有 PP 对朋友关系。B 公司有 MM 名员工,其中有 QQ 对朋友关系。朋友的朋友一定还是朋友。
每对朋友关系用两个整数 (X_i,Y_i)(Xi,Yi) 组成,表示朋友的编号分别为 X_i,Y_iXi,Yi。男人的编号是正数,女人的编号是负数。小明的编号是 11,小红的编号是 -1−1。
大家都知道,小明和小红是朋友,那么,请你写一个程序求出两公司之间,通过小明和小红认识的人最多一共能配成多少对情侣(包括他们自己)。
输入格式
输入的第一行,包含 44 个空格隔开的正整数 N,M,P,QN,M,P,Q。
之后 PP 行,每行两个正整数 X_i,Y_iXi,Yi。
之后 QQ 行,每行两个负整数 X_i,Y_iXi,Yi。
输出格式
输出一行一个正整数,表示通过小明和小红认识的人最多一共能配成多少对情侣(包括他们自己)。
输入输出样例
输入 #1复制
4 3 4 2 1 1 1 2 2 3 1 3 -1 -2 -3 -3
输出 #1复制
2
说明/提示
对于 30 \%30% 的数据,N,M \le 100N,M≤100,P,Q \le 200P,Q≤200;
对于 80 \%80% 的数据,N,M \le 4 \times 10^3N,M≤4×103,P,Q \le 10^4P,Q≤104;
对于 100 \%100% 的数据,N,M \le 10^4N,M≤104,P,Q \le 2 \times 10^4P,Q≤2×104。
思路讲解
用并查集来做,把小明认识的人包括自己放在一个集合里,把小红认识的人放在一个集合里,找两个集合人数最小值就行了
代码展示
#include<stdio.h>
int n,m,q,p;
int a,b,c,d;
int sum[10000];
int find(int x)//找最终父节点
{
if(sum[x]==x)return x;
return sum[x]=find(sum[x]);
}
void fun(int x,int y)
{
if(find(x)!=find(y))
sum[find(y)]=find(x);
}
int main()
{
scanf("%d %d %d %d",&n,&m,&p,&q);
int i,j;
for(i=1;i<=n;i++)
sum[i]=i;
for(i=1;i<=p;i++)
{
scanf("%d %d",&a,&b);
if(a<0)
{
a=-a;
b=-b;
}
fun(a,b);
}
for(i=1;i<=n;i++)
{
if(find(i)==find(1))
c++;
}
for(i=1;i<=m;i++)
sum[i]=i;
for(i=1;i<=q;i++)
{
scanf("%d %d",&a,&b);
if(a<0)
{
a=-a;
b=-b;
}
fun(a,b);
}
for(i=1;i<=m;i++)
{
if(find(i)==find(1))
d++;
}
if(c>d)
printf("%d",d);
else printf("%d",c);
return 0;
}