hdoj1068 2f

大学的第二年,有人开始研究学生之间的浪漫关系。“恋爱关系”是指一个女孩和一个男孩之间的关系。由于研究的原因,有必要找出满足这一条件的最大集合:没有两名学生曾“恋爱”过。这个项目的结果是这样一组学生的数量。

输入包含几个文本格式的数据集。每个数据集代表研究的一组主题,并说明如下:

学生人数
每个学生的描述,格式如下
student_identifier:(number_of_romantic_relations)学生标识1学生标识2学生标识3.

学生标识符:(0)

学生标识符是n个科目的0到n-1之间的整数.
对于每个给定的数据集,程序应该将包含结果的一行写入标准输出。
学校对n个学生(男女都有)进行的调查了,发现了某些学生暗生情愫,现在需要你选出一个最大的集合,这个集合内部没有两个人暗生情愫.学生的编号是0~n-1
输入

输入包含多组数据
第一行一个整数n,表示学生的数量.
接下来n行,第一个数表示一个学生编号,接下来一个数表示与他产生联系的人的数量,接下来是一组编号表示产生联系的学生编号.具体格式见样例.
你可以认为,数据是对称的,且不会出现奇环.
输出量
对于每组测试数据,输出一个整数,表示最多可以选出的人数.
样本输入
7
0: (3) 4 5 6
1: (2) 4 6
2: (0)
3: (0)
4: (2) 0 1
5: (1) 0
6: (2) 0 1
3
0: (2) 1 2
1: (1) 0
2: (1) 0
样本输出
5
2
输入没有指明那些是男孩/女孩。所以要拆点,把
i 拆成 i 跟 i’ 分别放入X、Y,原先U = V - M,所以 2U = 2V - 2M。 分析:

    故U = n - M'/2。
    代码:

#include<stdio.h>
#include<string.h>
#define N 1010
int map[N][N],mode[N],vis[N];
int t;
int find(int x)//寻找增广路! 找到返回1,否则返回0! 
{
	int i,j;
	for(i=0;i<t;i++)
	{
		if(map[x][i]&&!vis[i])//与x相连点,并且没有遍历到 
		{
			vis[i]=1;//标记为遍历过 
			if(!mode[i]||find(mode[i]))//i 点 没有和另一部分匹配或 和i配对的点 没有匹配! 
			{
				mode[i]=x;
				return 1;
			}
		}
	}
	return 0;
}
int main()
{
 
 
	while(scanf("%d",&t)!=EOF)
	{
		int i,j;
		memset(map,0,sizeof(map));
		memset(mode,0,sizeof(mode));
		for(i=0;i<t;i++)
		{
			int tt,x,y;
			scanf("%d: (%d)",&x,&tt);
			while(tt--)
			{
				scanf("%d",&y);
				map[x][y]=1;//标记为通路 
			}
		}
	
			int s=0;
			for(i=0;i<t;i++)
			{
				memset(vis,0,sizeof(vis));
				if(find(i))//增广路 
				{
				s++;
			    }
			}
			printf("%d\n",t-s/2);
	}
	return 0;
}
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

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

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值