题目链接:http://acm.hdu.edu.cn/showproblem.php?pid=1301
题目描述:在一个地方,有一些村庄,村庄之间有一些路,现告诉你输入n个村庄数目,接下来n-1行信息如下,第一个字母表示哪个村庄,第二个数表示这个村庄有k条路通往其他村庄,接下来的k对信息分别表示村庄通往的村庄和距离。求保留哪些路使得总路程最短(即维修费最短)
ac代码:
#include<iostream> #include<cstdio> #include<vector> #include<cstring> #include<algorithm> #include<queue> using namespace std; typedef long long ll; const ll maxn=2e10; ll d[26][26]; int vis[26]; //优先队列按从大到小的顺序排列的,重写小于号,与原号相反即可。 struct node{ int z,v,value; bool operator< (const node &a) const { return value>a.value; } }; int main() { int n; while(cin>>n&&n) { char c,ct; int k,ds; node pos; initd(); vector<node> a[26]; memset(vis,0,sizeof(vis)); for(int i=0;i<n-1;i++) { cin>>c>>k; for(int j=0;j<k;j++) { cin>>ct>>pos.value; pos.z=c-'A'; pos.v=ct-'A'; a[c-'A'].push_back(pos);//双向添加路。 pos.v=c-'A'; pos.z=ct-'A'; a[ct-'A'].push_back(pos); } } ll ans=0; priority_queue<node> s;//建立优先队列 vis[0]=1; for(int i=0;i<a[0].size();i++) s.push(a[0][i]); while(!s.empty()) { node p=s.top(); s.pop(); if(!vis[p.v]) { //cout<<"点"<<char('A'+p.v)<<" 价值 "<<p.value<<endl; ans+=p.value; vis[p.v]=1; for(int i=0;i<a[p.v].size();i++) s.push(a[p.v][i]); } } cout<<ans<<endl; } return 0; }