POJ 1251 Jungle Roads

 

POJ 1251 Jungle Roads

问题描述:

Lagrishan的一个热带岛屿上的行政长官有一个问题要解决。他决定把几年前得到的外国援助资金用于修建村庄之间的道路。但是丛林比道路多太多了,使道路网络的维护太过于昂贵了。理事会必须选择停止维修一些道路。上述左侧图显示当前所有使用中的道路,以及现在每月的维护费用。当然,村庄之间必需有一些公路能够相通,即使路线并不像以前一样短。行政长官想告诉理事会怎样才使每月的花费最小,并且所维持的道路,将连接所有村庄。上面的地图标记了村庄A到I。右边的图显示了每月能够维护道路的最小费用为216aacms。你的任务是编写一个程序,将解决这些问题。


输入:

输入包含的数据集个数在100以内,以0作为最后一行。每个数据集的第一行只包含一个表示村庄个数的数n,1<n<27,并且这n个村庄是由大写字母表里的前n个字母表示。接下来的n- 1行是由字母表的前n-1个字母开头。最后一个村庄表示的字母不用输入。对于每一行,以每个村庄表示的字母开头,然后后面跟着一个数字,表示有多少条道路可以从这个村到后面字母表中的村庄。如果k是大于0,表示该行后面会表示k条道路的k个数据。每条道路的数据是由表示连接到另一端村庄的字母和每月维修该道路的花费组成。维修费用是正整数的并且小于100。该行的所有数据字段分隔为一个空格。该公路网将始终连接所有的村庄。该公路网将永远不会超过75条道路。没有任何一个村庄会有超过15条的道路连接到其他村庄(之前或之后的字母)。在下面的示例输入,其中第一个数据集是与上面的地图相一致的。

输出

每行代表一组数据的答案:最小道路维护成本

样例输入:

9

A 2 B 12 I 25

B 3 C 10 H 40 I 8

C 2 D 18 G 55

D 1 E 44

E 2 F 60 G 38

F 0

G 1 H 35

H 1 I 35

3

A 2 B 10 C 40

B 1 C 20

0

样例输出

216

30

还是prim解决

#include<stdio.h>
#include<string.h>
#define inf 0x3fffffff
//普里姆prim  不是克鲁斯卡尔 
int map[30][30];

int prim(int n)
{
    int visit[30]={0};
    int dis[30];
    int sum,i,j,k,min;
    sum=0;
    for(i=0;i<n;++i)
        dis[i]=map[0][i];
    visit[0]=1;
    for(i=1;i<n;++i)
    {
        min=inf;
        k=0;
        for(j=0;j<n;++j)
        {
            if(!visit[j]&&min>dis[j])
            {
                min=dis[j];
                k=j;
            }
        }
        visit[k]=1;
        if(min!=inf)
            sum+=min;
        for(j=0;j<n;++j)
        {
            if(!visit[j]&&dis[j]>map[k][j])
                dis[j]=map[k][j];
        }
    }
    return sum;
}

int main()
{
	freopen("POJ 1251 Jungle Roads.txt","r",stdin);
    int n,len,k,i,j;
    char st[5],end[5];
    while(scanf("%d",&n),n)
    {
        for(i=0;i<n;++i)
            for(j=0;j<i;++j)
                map[i][j]=map[j][i]=inf;
        for(i=1;i<n;++i)
        {
            scanf("%s%d",st,&k);
            while(k--)
            {
                scanf("%s%d",end,&len);
                if(len<map[st[0]-'A'][end[0]-'A'])
                {
                    map[st[0]-'A'][end[0]-'A']=map[end[0]-'A'][st[0]-'A']=len;
                }
            }
        }
        printf("%d\n",prim(n));
    }
    return 0;
}


  • 1
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值