海洋之心


私信TA

用户名:wanggongsheng

访问量:132614

签 名:

等  级
排  名 18
经  验 21668
参赛次数 3
文章发表 163
年  龄 26
在职情况 学生
学  校
专  业 计算机技术

  自我简介:

读研ing,平时不登录dotcpp

http://www.dotcpp.com/oj/problem1435.html 
1.使用并查集
2.使用一个结构体数组保存输入的桥梁的数据
3.根据每个桥梁断开的天数进行排序,从大到小进行排序,反向思考。从最后一个断掉的桥梁开始修桥,如
  果修的桥连通了两个不同的分支,并且和上一个连通两个不同分支的桥梁对应的天数不是同一天,那么天
  数加一。
4.使用一个变量last_day记录上一个连通两个不同的分支的桥梁断裂的天数。
5.然后就是并查集的操作。
#include<iostream>
#include<cstdio>
#include<algorithm>
#define maxn 100010 
using namespace std;
int m,n,parent[maxn],days;
typedef struct Qiao{
	int start,end,day;
}Qiao;
Qiao Bridge[maxn];
int cmp(Qiao x,Qiao y){  return x.day>y.day; }
int find(int son)
{
	if(parent[son]==son) return son;
	else return parent[son]=find(parent[son]);
}
int unite(int x,int y)//返回值记录是否是同一个连通的分支 
{
	int boss1=find(x);
	int boss2=find(y);
	if(boss1!=boss2)
	{
		parent[boss1]=parent[boss2];
		return 0; 
	}
	return 1;
}
int main(void)
{
	scanf("%d%d",&n,&m);
	for(int i=1;i<=n;i++) parent[i]=i; 
	for(int i=1;i<=m;i++) 
		scanf("%d%d%d",&(Bridge[i].start),&(Bridge[i].end),&(Bridge[i].day)); 
	sort(Bridge+1,Bridge+m+1,cmp);
	int last_day=-1;
	for(int i=1;i<=m;i++)
	{
		/*
		int boss1=find(Bridge[i].start);
		int boss2=find(Bridge[i].end);
		if(boss1 != boss2)
		{
			unite();	
		} 
		*/
		int able=unite(Bridge[i].start,Bridge[i].end);
		if(Bridge[i].day != last_day && able==0) days++,last_day=Bridge[i].day;
	}
	printf("%d",days);
	return 0;
}

解题思路:





注意事项:





参考代码:

 

0.0分

1 人评分

  评论区

  • «
  • »