HDOJ 1827 Summer Holiday

来源:互联网 发布:索多玛120天 知乎 编辑:程序博客网 时间:2024/06/05 15:01


Summer Holiday

Time Limit: 10000/1000 MS (Java/Others)    Memory Limit: 32768/32768 K (Java/Others)
Total Submission(s): 3540    Accepted Submission(s): 1617


Problem Description

To see a World in a Grain of Sand
And a Heaven in a Wild Flower,
Hold Infinity in the palm of your hand
And Eternity in an hour.
                  —— William Blake

听说lcy帮大家预定了新马泰7日游,Wiskey真是高兴的夜不能寐啊,他想着得快点把这消息告诉大家,虽然他手上有所有人的联系方式,但是一个一个联系过去实在太耗时间和电话费了。他知道其他人也有一些别人的联系方式,这样他可以通知其他人,再让其他人帮忙通知一下别人。你能帮Wiskey计算出至少要通知多少人,至少得花多少电话费就能让所有人都被通知到吗?

 

Input

多组测试数组,以EOF结束。
第一行两个整数N和M(1<=N<=1000, 1<=M<=2000),表示人数和联系对数。
接下一行有N个整数,表示Wiskey联系第i个人的电话费用。
接着有M行,每行有两个整数X,Y,表示X能联系到Y,但是不表示Y也能联系X。

 

Output

输出最小联系人数和最小花费。
每个CASE输出答案一行。

 


Sample Input

12 162 2 2 2 2 2 2 2 2 2 2 2 1 33 22 13 42 43 55 44 66 47 47 127 88 78 910 911 10
 

Sample Output

3 6


#include <bits/stdc++.h>using namespace std;#define mst(a,b) memset(a,(b),sizeof(a))#define f(i,a,b) for(int i=a;i<=b;i++)#define maxn 2005const int INF=2e9;vector<int>mp[maxn];int n,m,num,top,suo;int dfn[maxn],low[maxn],w[maxn],belong[maxn],stack_[maxn],cost[maxn];bool instack_[maxn],ru[maxn];void tarjan(int u){    dfn[u]=low[u]=++num;    stack_[++top]=u;    instack_[u]=true;    int v;    for(int i=0;i<mp[u].size();i++)    {        v=mp[u][i];        if(!dfn[v])        {            tarjan(v);            low[u]=min(low[u],low[v]);        }        else if(instack_[v])            low[u]=min(low[u],dfn[v]);    }    if (low[u]==dfn[u])    {        suo++;        do        {            v=stack_[top--];            belong[v]=suo;            instack_[v]=false;        }while(v!=u);    }}void solve(){    int v;    mst(dfn,0);    mst(instack_,false);    num=top=suo=0;    f(i,1,n)    {        if(!dfn[i])            tarjan(i);    }    mst(ru,false);    f(i,1,n)    {        for(int j=0;j<mp[i].size();j++)        {            v=mp[i][j];            if(belong[i]!=belong[v])                ru[belong[v]]=true;        }    }    f(i,1,suo)        cost[i]=INF;    f(i,1,n)    {        if(!ru[belong[i]])            cost[belong[i]]=min(cost[belong[i]],w[i]);    }    int sum1=0,sum2=0;    f(i,1,suo)    {        if(!ru[i])        {            sum1++;            sum2+=cost[i];        }    }    printf("%d %d\n",sum1,sum2);}int main(){    while(~scanf("%d%d",&n,&m))    {        f(i,1,n)        {            scanf("%d",&w[i]);            mp[i].clear();        }        int x,y;        f(i,1,m)        {            scanf("%d%d",&x,&y);            mp[x].push_back(y);        }        solve();    }    return 0;}




0 0
原创粉丝点击