1087. All Roads Lead to Rome (30)

#include<unordered_map>
#include<bitset>
#include<iostream>
#include<string>
#include<vector>
using namespace std;
const int N=300;
int pos;
string name[300];
int s2i(string s)
{
  static  unordered_map<string,int>nth;
  auto it=nth.find(s);
  if(it!=nth.end())
    return it->second;
  else{
    name[pos]=s;
    nth[s]=pos;
    return pos++; }
}
struct node{int to,len;node(int a,int b):to(a),len(b){}};
vector<node>ed[N];
int dis[N],pre[N],allval[N],used[N],num[N],cnt[N];
int src,dst,val[N];
void dijkstra()
{
  fill_n(dis,N,1<<30);
  dis[src]=0;
  allval[src]=val[src];
  num[src]=0;
  cnt[src]=1;
  while(true)
    {
      
      int next=-1;
      for(int mmin=1<<30,i=0;i<pos;++i)
	if(!used[i]&&dis[i]<mmin) mmin=dis[next=i];
      if(next==-1)break;
      used[next]=true;
      for(auto x:ed[next])
	if(!used[x.to])
	  {
	    if(dis[x.to]>dis[next]+x.len)
	      {
		cnt[x.to]=cnt[next];
		dis[x.to]=dis[next]+x.len;
		pre[x.to]=next;
		allval[x.to]=allval[next]+val[x.to];
		num[x.to]=num[next]+1;
	      }else if(dis[x.to]==dis[next]+x.len)
	      {
		cnt[x.to]+=cnt[next];
		if(allval[x.to]<allval[next]+val[x.to]||
		   allval[x.to]==allval[next]+val[x.to]&&
		   (num[x.to]>num[next]+1))
		  {
		    pre[x.to]=next;
		    allval[x.to]=allval[next]+val[x.to];
		    num[x.to]=num[next]+1;
		  }//if
	      }//else if
	  }//if
    }//while
}
void path(int k){
  if(k!=src) path(pre[k]);
  static int first=0;
  cout<<(first++?"->":"")<<name[k];
}
int main(){
  dst=s2i("ROM");
  int n,k;
  string sa,sb;
  cin>>n>>k>>sa;
  src=s2i(sa);
  for(int i=1,tmp;i<n;++i)
    {cin>>sa>>tmp; val[s2i(sa)]=tmp; }
  for(int i=0,len,t1,t2;i<k;++i){
    cin>>sa>>sb>>len;
    t1=s2i(sa),t2=s2i(sb);
    ed[t1].emplace_back(t2,len);
    ed[t2].emplace_back(t1,len);
  }
  dijkstra();
  printf("%d %d %d %d\n",cnt[dst],dis[dst],allval[dst],allval[dst]/num[dst]);
  path(dst);
}
dijkstra算法,不过平常在松弛路径是只要保持pre,dis,used就行,这里还要保持最短路径数cnt,最短路径上最多城市数num,最短路径上最大累计happy值allval,其他的没什么,注意cnt的更新方式即可

你可能感兴趣的:(1087. All Roads Lead to Rome (30))