1. 程式人生 > >叢林中的路

叢林中的路

edi 正整數 lag 導致 一個 void std bre http

總時間限制:
1000ms
內存限制:
65536kB
描述

技術分享

熱帶島嶼Lagrishan的首領現在面臨一個問題:幾年前,一批外援資金被用於維護村落之間的道路,但日益繁茂的叢林無情的侵蝕著村民的道路,導致道路維修開銷巨大,長老會不得不放棄部分道路的維護。上圖左側圖顯示的是正在使用道路的簡圖以及每條路每個月的維修費用(單位為aacms)。現在長老會需要提出一種方案,即需要保證村落之間都可以互相到達,又要將每個月的道路維修費用控制在最小。村子編號為從A到I。上圖右側顯示的方案最小維修開銷為216 aacms每月。

輸入
輸入包含1~100個數據集,最後一行為0.每個數據集第一行為村落數目n, 1 < n < 27,依次用字母表的前n個字母標記。接下來有n-1行,每行的第一個數據便是按字母順序排列的村子編號(不包括最後一個村莊)。每個村莊後面的數據k代表該村莊通往編號在其之後的村莊的道路數目,如A 2 B 12 I 25,代表A村莊有2個編號在A之後的村莊和其相連。若k大於0,k後面會依次給出這k個村莊的編號以及各自到起始村莊的道路維修費用,如A 2 B 12 I 25,代表A和B之間道路維修費用為12, A和I之間道路維修費用為25(維修費用為不超過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
keuskal最小生成樹
#include<cstdio>
#include<iostream>
#include<algorithm>
#include
<cstring> using namespace std; const int N = 300; int father[N];int n; int find(int x) { if(father[x]!=x)father[x]=find(father[x]); return father[x]; } int num=0; struct node{ int x, y,w; bool operator < (const node &a)const{ return w<a.w; } }edge[N
*N]; void add_edge(int x,int y,int w) { edge[++num].x=x,edge[num].y=y,edge[num].w=w; } void kruskal() { sort(edge+1,edge+num+1); int cnt=0,ans=0; for(int i=1;i<=num;i++) { int fx=find(edge[i].x),fy=find(edge[i].y); if(fx!=fy) { father[fx]=father[fy]; cnt++; ans+=edge[i].w; } if(cnt==n-1)break; } printf("%d\n",ans); return; } int main() { int a; char q[10]; while(11101001) { memset(father,0,sizeof(father)); memset(edge,0,sizeof(edge)); scanf("%d",&n); if(n==0) break; num=0; for(int i=1;i<n;i++) { father[i]=i; scanf("%s %d",q,&a); char p[10]; int aa; for(int i=1;i<=a;i++) { scanf("%s %d",p,&aa); add_edge(q[0]-64,p[0]-64,aa); } } kruskal(); } return 0; }

叢林中的路