2609 最苗条的生成树(边权差值最小 生成树)

本文探讨了在无向联通图中寻找苗条度最小的生成树问题,通过枚举最小边并应用Kruskal算法,详细解释了如何确定生成树的苗条度。文章包含代码实现和理论依据,适合对图论和算法设计感兴趣的读者。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

2609 最苗条的生成树

定义一颗树的苗条度为这棵树的最大边权与最小边权的差值。

现在有一个n个点m条边的无向联通图,求苗条度最小的生成树的苗条度是多少。

如图所示的数据中:最优的选取方案选取的生成树的三条边分别为(1-4,4-2,1-3),

所以答案为100-80=20。

输入

第1行:两个正整数n,m,n表示图中点的个数,m表示图中边的个数。(2<=n<=100,0<=m<=(n*(n − 1)/2))
第2行-第m+1行:每行3个正整数,u,v,w,表示u和v之间有一条权值为w的边。(1<=u,v<=n,1<=w<=10000)

输出

输出一个整数表示苗条度最小的生成树的苗条度。

输入样例

4 6
1 2 10
1 3 100
1 4 90
2 3 20
2 4 80
3 4 40

输出样例

20

思路:

        本想水一发,没想到A了,做法的是枚举最小边然后到比该边大的边里找最小生成树,

事实这个做法是没有问题的。

因为:

        因为根据Kruskal算法的原理,最小生成树的最短边确定后,最长边也相应确定,

他们的差值就确定(参见《算法导论》)。所以可以枚举最短边求出生成树。 

       具体来说,一个图的最小生成树不一定是唯一的,但是组成这些最小生成树的

各个边的权值一定都是一一对应相同的。不会出现这种一个树上有两个边权值a+b等于

另外一颗树上两个边c+d,然后这两个树都是最小生成树的情况。  

上述内容大佬博客拼接而成。。。

代码实现:

#include<iostream>
#include<cstring>
#include<cmath>
#include<queue>
#include<map>
#include<cstdio>
#include<algorithm>
#define LL long long
#define INF 0x3f3f3f3f
using namespace std;
const int N=2e5+100;
const int M=4e5+100;
const  int mod=1e9+7;
struct Node {
  int l,r,val;
} err[M];
bool cmp(Node aa,Node bb) {
  return aa.val<bb.val;
}
int fat[N];
int find(int x) {
  return x==fat[x]?x:fat[x]=find(fat[x]);
}
int main() {
#ifdef MYHOME
  freopen("input.txt","r",stdin);
#endif
  int maxs,n,m,mini,ans;
  while(cin>>n>>m) {
    mini=ans=INF;
    maxs=0;
    for(int i=1; i<=n; i++)fat[i]=i;
    for(int i=1; i<=m; i++) {
      cin>>err[i].l>>err[i].r>>err[i].val;
    }
    sort(err+1,err+1+m,cmp);
    for(int i=1; i<=)

    }
  return 0;
}

THE END;

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值