poj3134 Command Network --- 最小树形图

来源:互联网 发布:企业数据备份解决方案 编辑:程序博客网 时间:2024/06/05 08:59

新单词unidirectional get T T

求有向图上,以某点为根的,最小生成树

参考别人的模板


#include<cstdio>#include<cstring>#include<vector>#include<queue>#include<iostream>#include<algorithm>#include<cmath>#define inf 2000000000using namespace std;struct node1{    double x,y;}p[110];struct node{    int u,v;    double w;}e[10010];double ans,in[110];int n,m,r,cnt,id[110],vis[110],pre[110];int zhuliu(int r,int V,int E){    ans=0;    while(1)    {        int u,v,i;        //找最小入边        for(i=0;i<=V;i++)            in[i]=inf;        for(i=0;i<E;i++)        {            u=e[i].u;            v=e[i].v;            if(e[i].w<in[v] && u!=v)            {                pre[v]=u;                in[v]=e[i].w;            }        }        for(i=0;i<V;i++)//判断图不连通 直接返回            if(i!=r&&in[i]==inf) return -1;        //找环        cnt=0;//记缩点后的联通块编号        memset(id,-1,sizeof id);//id[i]表示i缩点后在哪个联通块        memset(vis,-1,sizeof vis);        in[r]=0;        for(i=0;i<V;i++)        {         //   printf("i:%d ini:%.2lf\n",i,in[i]);            ans+=in[i];            v=i;            while(vis[v]!=i&&v!=r&&id[v]==-1)//找环            {                vis[v]=i;                v=pre[v];            }            if(v!=r&&id[v]==-1)//缩点            {                for(u=pre[v];u!=v;u=pre[u])                    id[u]=cnt;                id[v]=cnt++;            }        }        if(cnt==0) break;//无环        //建新图        for(i=0;i<V;i++)            if(id[i]==-1) id[i]=cnt++;        for(i=0;i<E;i++)        {            u=e[i].u;            v=e[i].v;            e[i].u=id[u];            e[i].v=id[v];            if(id[u]!=id[v]) e[i].w-=in[v];        }        V=cnt;        r=id[r];    }    return 1;}int main(){    int i,a,b;    while(~scanf("%d%d",&n,&m))    {        for(i=1;i<=n;i++)            scanf("%lf%lf",&p[i].x,&p[i].y);        for(i=0;i<m;i++)        {            scanf("%d%d",&a,&b);            e[i].u=a-1;            e[i].v=b-1;            if(a==b) e[i].w=inf;//除掉自环            else e[i].w=sqrt((p[a].x-p[b].x)*(p[a].x-p[b].x)+(p[a].y-p[b].y)*(p[a].y-p[b].y));        }        if(zhuliu(0,n,m)==1)            printf("%.2lf\n",ans);        else printf("poor snoopy\n");    }    return 0;}


0 0
原创粉丝点击