POJ 2377 最大生成树(prim,kruskal)

来源:互联网 发布:2k17得分后卫身体数据 编辑:程序博客网 时间:2024/05/12 19:13

题目:http://poj.org/problem?id=2377

最大生成树,改一改prim即可,把大小换一换,最初graph都fill为-1。

POJ就好搞一些无聊的重边,要把最大的数据放入graph。

#include<cstdio>#include<iostream>#include<queue>#include<string>#include<cstring>#include<map>using namespace std;const int maxn=1005;const int maxcost=999999999;int  graph[maxn][maxn],lowcost[maxn],visit[maxn][maxn];int prim(int s,int n){    int lowcost[maxn];    int mst[maxn];    int i,j,minn,minid,sum=0;    for(i=1;i<=n;i++){             //lowcost初始化        lowcost[i]=graph[s][i];        mst[i]=s;    }    mst[s]=0;    lowcost[s]=maxcost;    for(i=2;i<=n;i++){        minn=-1;        minid=0;        for(j=1;j<=n;j++){            if(lowcost[j]>minn&&lowcost[j]!=maxcost){                   minn=lowcost[j];                minid=j;            }        }      //cout<<minn<<endl;        if(minn==-1)            return -1;        //不连通        //printf("%c - %c : %d\n", mst[minid] + 'A' - 1, minid + 'A' - 1, min);        sum+=minn;        lowcost[minid]=maxcost;        for(j=1;j<=n;j++){                if(graph[minid][j]>lowcost[j]){                lowcost[j]=graph[minid][j];                mst[j]=minid;               }        }    }    return sum;}int main(){    int n,m;    int x,y,val,maxval=0,s=0;    scanf("%d%d",&n,&m);    fill(graph[0],graph[0]+maxn*maxn,-1);    for(int i=0;i<m;i++){        scanf("%d%d%d",&x,&y,&val);        if(val>graph[x][y])            graph[x][y]=graph[y][x]=val;        if(val>maxval){            maxval=val;            s=x;        }    }    printf("%d\n",prim(s,n));    return 0;}
Kruskal则不需考虑重边,因为find找爸爸判断那里过不去。
#include<cstdio>#include<iostream>#include<cstring>#include<algorithm>using namespace std;const int inf=999999999;int n,m,q,fa[1010];struct edge{    int x,y,len;}e[20005];bool cmp(edge a,edge b){    return a.len>b.len;}int find(int x){    return fa[x] != x ? fa[x] = find(fa[x]) : x;}int kruskal(){    for(int i=0;i<=n;i++)        fa[i]=i;    sort(e,e+m,cmp);    int cnt=0;    int sum=0;    for(int i=0;i<m;i++){        int x=e[i].x,y=e[i].y;        int t1=find(e[i].x);        int t2=find(e[i].y);        if(t1!=t2){            sum+=e[i].len;            fa[t2]=t1;            cnt++;        }        if(cnt==n-1)            break;    }    if(cnt<n-1)        return -1;    else        return sum;}int main(){    scanf("%d%d",&n,&m);    for(int i=0;i<m;i++)        scanf("%d%d%d",&e[i].x,&e[i].y,&e[i].len);    printf("%d\n",kruskal());    return 0;}