HDU1272_无向图的判环

1.题目链接。题目大意其实很清楚了,就是给你一些点对,这些点对之间有边相连。这些边连起来组成了一个迷宫,现在的问题是从迷宫上的任意一个点到另外一个点要求只能有一条路径。判断给出的图是否是满足条件的。看到这个要求其实很简单了,就是图的生成树嘛,n个顶点需要n-1条边,至于无向图的联通判断我们采用并查集,因为如果一条边上的两个点具有相同的祖先,那么一定是有环存在的,所以我们对输入的每一条边进行并查操作,如果是有公共的祖先,那么不用再加入有一个联通分量,但是这是我们标志是否有环的那个flag要设置成true。如果没有,并到一起,并且边数加一。最后统计边数是否是点数减一即可。至于点数的计算,我们使用set,每次输入的两个点,insert进去。这样比较size和边数即可。代码实现如下:

#include<iostream>
#include<set>
#pragma warning(disable:4996)
using namespace std;
const int  N = 1e5 + 10;
int pre[N];
int find(int a)
{
	return a == pre[a] ? a : pre[a] = find(pre[a]);
}
void join(int a, int b)
{
	int x = find(a);
	int y = find(b);
	if (x != y)
	{
		pre[x] = y;
	}
}
int main()
{
	int u, v;
	while (~scanf("%d%d", &u, &v)&&u!=-1&&v!=-1)
	{
		for (int i = 0; i < N; i++)
			pre[i] = i;
		if (u == 0 && v == 0)
		{
			puts("Yes");
			continue;
		}
		set<int>s;
		int fx = find(u);
		int fy = find(v);
		pre[fx] = fy;
		int cnt = 0;
		int flag = 0;
		s.insert(u);
		s.insert(v);
		cnt++;
		while (scanf("%d%d", &u, &v))
		{
			if (!u && !v)break;
			int x = find(u);
			int y = find(v);
			s.insert(u);
			s.insert(v);
			cnt++;
			if (x != y)
			{
				pre[x] = y;
			}
			else
			{
				flag = 1;
			}
		}
		if (flag || (cnt + 1) != s.size())
		{
			puts("No");
		}
		else
		{
			puts("Yes");
		}
	}
	return 0;
}

 

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值