1. 程式人生 > 其它 >L3-011 直搗黃龍 (天梯賽)

L3-011 直搗黃龍 (天梯賽)

很明顯就是一道最短路問題 並且記錄路徑

還有一個坑點是 第一個輸出的是最短路徑數目 不是經過節點數目!!!

最後就是輸出路徑 我開始一直寫成 pre[u]==mp[S]了 導致老是路徑輸出少一個

最後才發現錯誤 應該是u==mp[S] !!!!

#include<bits/stdc++.h>
using namespace std;
#define lowbit(x) x&(-x)
#define ll long long
const int maxn=205;
int n,k,cnt,tot;
string S,T;
int head[maxn],dis[maxn],dp[maxn],sum[maxn],pre[maxn],res[maxn];
struct node{
	int to,next,w;
}edg[maxn*maxn];
void add(int u,int v,int w){
	edg[++tot].next=head[u];head[u]=tot;edg[tot].to=v;edg[tot].w=w;
}
map<string,int>mp;
map<int,string>kk;
int val[maxn];
void spfa();
void dfs(int);
int main(){
	cin>>n>>k>>S>>T;
	mp[S]=++cnt;mp[T]=++cnt;
	kk[mp[S]]=S;kk[mp[T]]=T;
	for(int i=1;i<n;i++){
		string t;int cc;
		cin>>t>>cc;
		mp[t]=++cnt;
		kk[mp[t]]=t;
		val[mp[t]]=cc;
	}
	for(int i=1;i<=k;i++){
		string ss,tt;int cc;
		cin>>ss>>tt>>cc;
		add(mp[ss],mp[tt],cc);
		add(mp[tt],mp[ss],cc);
	}
	spfa();
	dfs(mp[T]);cout<<endl;
	cout<<res[mp[T]]<<" "<<dis[mp[T]]<<" "<<-dp[mp[T]];
     return 0;
}
queue<int>Q;
int vis[maxn];
void spfa(){
	Q.push(mp[S]);
	vis[mp[S]]=1;
	memset(dis,0x7f,sizeof(dis));
	memset(dp,0x7f,sizeof(dp));
	memset(sum,0x7f,sizeof(sum));
	sum[mp[S]]=dp[mp[S]]=0;dis[mp[S]]=0;
	res[mp[S]]=1;
	while(!Q.empty()){
		int u=Q.front();
		vis[u]=0;
		Q.pop();
		for(int i=head[u];i;i=edg[i].next){
			int to=edg[i].to,w=edg[i].w;
			if(dis[to]>dis[u]+w){
				dis[to]=dis[u]+w;
				dp[to]=dp[u]-val[to];
				sum[to]=sum[u]-1;
				res[to]=res[u];
				pre[to]=u;
				if(!vis[to]){
					vis[to]=1;
					Q.push(to);
				}
			}
			else if(dis[to]==dis[u]+w){
				res[to]+=res[u];
				if(sum[to]>sum[u]-1){
					sum[to]=sum[u]-1;
					dp[to]=dp[u]-val[to];
					pre[to]=u;
				}
				else if(sum[to]==sum[u]-1){
					if(dp[to]>dp[u]-val[to]){
						dp[to]=dp[u]-val[to];
						pre[to]=u;
					}
				}
			}
		}
	}
}
void dfs(int u){
	if(u==mp[S]){
		cout<<kk[mp[S]];
		return;
	}
	dfs(pre[u]);
	cout<<"->"<<kk[u];
}