• P1396 营救+生成树


    算法

    最小生成树

    思路

    其实就是一道最小生成树的模板题,我在这里用的是kruskal算法,唯一需要注意的是每加入一条边都要判断s,t是不是在一个集合里面,这样就可以顺利AC了。(排序了)

    代码

    #include<cstdio>
    #include<cstring>
    #include<iostream>
    #include<algorithm>
    using namespace std;
    int fa[10005];
    struct node{
        int x,y,z;
    }; 
    node way[20010];
    int n,m,s,t,tot=0;
    int com(const node &c,const node &d)
    {
        return c.z<d.z;
    }
    int find(int g)  //找到该元素所在集合的代表元素
    {
        if (fa[g]!=g)
           fa[g]=find(fa[g]);
        return fa[g];
    }
    int unionn(int s1,int s2)  //合并集合的过程
    {
        int r1=find(s1);
        int r2=find(s2);
        if (r1!=r2)
           fa[r1]=r2;
    }
    int js()
    {
        int i,j,k;
        k=1;
        i=1;
        while (k<n)
        {
            while (find(way[i].x)==find(way[i].y))
                i++;
            tot=max(way[i].z,tot);   //因为求的是最大值,所以用了一个max,其实没必要这么麻烦,因为边一定是从大到小的,后加入的边一定较大,可以直接写tot=way[i].z;
            unionn(way[i].x,way[i].y);  //这里就是一个并查集处理
            k++;
            if (find(s)==find(t))  //判断,自认为是这道题最重要的细节
               break;
        }
    }
    int main()
    {
        scanf("%d%d%d%d",&n,&m,&s,&t);
        int i;
        for (i=1;i<=m;i++)
        {
           scanf("%d%d%d",&way[i].x,&way[i].y,&way[i].z);
        }
        for (i=1;i<=n;i++)
          fa[i]=i;
        sort(way+1,way+1+m,com);  //把边从小到大排序
        js();
        printf("%d",tot);
        return 0;
    }
    

      

  • 相关阅读:
    1月27日 常用函数
    1月25日 JavaScript的DOM操作
    1月25日 JavaScript简介与语法
    1月24日 样式表案例
    5月14日 数字顺序打印并求和
    5月14日 根据班级人数,求平局分,最大值,最小值
    5月14日 九九乘法口诀
    5月14日 打印100以内与7有关的数
    5月14日 函数练习 100以内奇数的和
    5月14日 枚举类型
  • 原文地址:https://www.cnblogs.com/ruanmowen/p/12727698.html
Copyright © 2020-2023  润新知