洛谷 P3366 【模板】最小生成树 如题

P3366 【模板】最小生成树

  • 时空限制1s / 128MB

题目描述

如题,给出一个无向图,求出最小生成树,如果该图不连通,则输出orz

输入输出格式

输入格式:

 

第一行包含两个整数N、M,表示该图共有N个结点和M条无向边。(N<=5000,M<=200000)

接下来M行每行包含三个整数Xi、Yi、Zi,表示有一条长度为Zi的无向边连接结点Xi、Yi

 

输出格式:

 

输出包含一个数,即最小生成树的各边的长度之和;如果该图不连通则输出orz

 

输入输出样例

输入样例#1: 
4 5
1 2 2
1 3 2
1 4 3
2 3 4
3 4 3
输出样例#1: 
7

说明

时空限制:1000ms,128M

数据规模:

对于20%的数据:N<=5,M<=20

对于40%的数据:N<=50,M<=2500

对于70%的数据:N<=500,M<=10000

对于100%的数据:N<=5000,M<=200000

样例解释:

所以最小生成树的总边权为2+2+3=7

------------------------------------------------------------------------------------------------------------

Kruskal(并查集+贪心实现):

 

 1 #include<stdio.h>
 2 #include<string.h>
 3 #include<iostream>
 4 #include<algorithm>
 5 #define maxn 233333
 6 using namespace std;
 7 struct node{
 8     int fr,to,w;
 9 };
10 node e[maxn];
11 int n,m,cnt,num,fa[maxn],ans;
12 bool cmp(node,node);
13 int getf(int);
14 int main(){
15     scanf("%d %d",&n,&m);
16     for(int i=1;i<=n;i++) fa[i]=i;
17     cnt=0;num=0;ans=0;
18     for(int i=1;i<=m;i++){
19         int x,y,z;
20         scanf("%d %d %d",&x,&y,&z);
21         e[++cnt].fr=x;e[cnt].to=y;e[cnt].w=z;
22     }
23     sort(e+1,e+1+m,cmp);
24     for(int i=1;i<=m;i++){
25         if(num==n-1) break;
26         int af,bf;
27         af=getf(e[i].fr);
28         bf=getf(e[i].to);
29         if(af!=bf){
30             fa[af]=bf;
31             num++;
32             ans+=e[i].w;
33         }
34     }
35     if(num<n-1) printf("orz");
36     else printf("%d",ans);
37     return 0;
38 }
39 int getf(int x){
40     if(fa[x]==x) return x;
41     return fa[x]=getf(fa[x]);
42 }
43 bool cmp(node x,node y){
44     return x.w<y.w;
45 }
Kruskal

 

posted @ 2017-11-02 19:45  lpl_bys  阅读(266)  评论(0编辑  收藏  举报