#include <algorithm>
#include <iostream>
#include <vector>
using namespace std;
struct Road{
int from;
int to;
int distance;
};
vector<Road>road;
int father[26];
int height[26];
void initial(int n){
for(int i=1;i<=n;i++){
father[i]=i;
height[i]=0;
}
return ;
}
bool compare(Road a,Road b){
return a.distance<b.distance;
}
int Find(int a){
if(father[a]==a) return a;
return father[a]=Find(father[a]);
}
void Union(int x,int y){
int rootx=Find(x);
int rooty=Find(y);
if(rootx!=rooty){
if(height[rootx]<height[rooty]){
father[rootx]=rooty;
}else if(height[rootx]>height[rooty]){
father[rooty]=rootx;
}else{
father[rootx]=rooty;
height[rooty]++;
}
}
return ;
}
int kruskal(int cityNum){
// 初始化
initial(cityNum);
// 边进行排序
sort(road.begin(),road.end(),compare);
int res=0;
for(auto it=road.begin();it!=road.end();it++){
if(Find(it->from)!=Find(it->to)){
res+=it->distance;
Union(it->from, it->to);
}
}
return res;
}
int main() {
int cityNum;
while(cin>>cityNum){
if(cityNum==0) break;
road.clear();
int num=cityNum-1;
while(num--){
char a,b;
int roadNum;
int distance;
cin>>a>>roadNum;
for(int i=0;i<roadNum;i++){
cin>>b>>distance;
road.push_back({a-'A',b-'A',distance});
}
}
cout<<kruskal(cityNum)<<endl;
}
return 0;
}
// 64 位输出请用 printf("%lld")
本质就是kruskal算法,找最小生成树,麻烦的一点就是读入边进行表示

京公网安备 11010502036488号