码迷,mamicode.com
首页 > 其他好文 > 详细

[USACO08OCT]:打井Watering Hole(MST)

时间:2019-07-10 16:31:25      阅读:72      评论:0      收藏:0      [点我收藏+]

标签:节点   col   mes   str   div   bool   void   using   题意   

题意:有N个牧场,每个牧场修水井花费Wi,连接牧场花费Pij,问最小花费,使得每个牧场要么有水井,要么和有水井的牧场有通道。

思路:加一个格外的节点O,连接O表示修井,边权是修井的费用。     那么这N+1个点求最MST即可。

刘同学想到的解法: 先找到修井费用最低的的牧场,然后和上面一样,由于最低的那个必选,所以异曲同工。

#include<bits/stdc++.h>
#define rep(i,a,b) for(int i=a;i<=b;i++)
using namespace std;
const int maxn=310;
const int maxm=maxn*maxn;
int fa[maxn],t[maxn],a[maxn][maxn],tot;
struct in{
    int len,u,v;
}s[maxm];
bool cmp(in w,in q) {
    return w.len<q.len;
}
void add(int u,int v,int len){
    tot++; s[tot].u=u; s[tot].v=v; 
    s[tot].len=len;
}
int find(int x){
    if(x!=fa[x]) return fa[x]=find(fa[x]);
    return x;
}
int main()
{
    int N,M,ans=0;
    scanf("%d",&N);
    rep(i,1,N) scanf("%d",&t[i]);
    rep(i,1,N) rep(j,1,N) {
        scanf("%d",&a[i][j]);
        if(a[i][j]) add(i,j,a[i][j]);
    }
    rep(i,0,N) fa[i]=i;
    rep(i,1,N) add(0,i,t[i]);
    sort(s+1,s+tot+1,cmp);
    rep(i,1,tot) {
        int fu=find(s[i].u);
        int fv=find(s[i].v);
        if(fu==fv) continue;
        fa[fu]=fv; ans+=s[i].len;
     }
     printf("%d\n",ans);
    return 0;
}

 

[USACO08OCT]:打井Watering Hole(MST)

标签:节点   col   mes   str   div   bool   void   using   题意   

原文地址:https://www.cnblogs.com/hua-dong/p/11164702.html

(0)
(0)
   
举报
评论 一句话评论(0
登录后才能评论!
© 2014 mamicode.com 版权所有  联系我们:gaon5@hotmail.com
迷上了代码!