NOIP2018原創模擬賽DAY1 密室
阿新 • • 發佈:2018-09-24
deque 模板題 最優 無向圖 push_back har 一個人 total esp
題目描述:https://www.luogu.org/problemnew/show/U38181
讀完題之後,我門發現這是一道裸的最短路,寫個我們大家都喜歡的SPFA就可以秒過
考場上的思維自以為沒有什麽問題,隨手寫完就交了
考完一看發現掛了,一個點都沒過,就有點蒙,然後發現是Re
下面的這行代碼大家一定要記住(以後都這麽寫)
long long main()
這個悲慘的故事大家一定要銘記在心,然而你以為這就是事情的全部嗎?
不不不,我國服被卡王今天就要卡死在這裏
我們會發現,這道題目在最後有一個分類討論,就是有可能Harry一個人去兩個房間會更快(主角光環就是nb)
因為是無向圖,所以天真的我認為只用判斷一次,然而我還是太年輕,Harry先去不同的房間好肥的時間可能不同(出題人太巨了)
然後除了這些也就沒有什麽思維難度了,基本上是個模板題
下面給出代碼:
#include<iostream> #include<cmath> #include<cstdio> #include<cstdlib> #include<cstring> #include<string> #include<algorithm> #include<queue> using namespace std; inline long long min(long long a,long longb){return a<b?a:b;} inline long long max(long long a,long long b){return a>b?a:b;} inline long long rd() { long long x=0,f=1; char c=getchar(); for(;!isdigit(c);c=getchar()) if(c==‘-‘) f=-1; for(;isdigit(c);c=getchar()) x=x*10+c-‘0‘; return x*f; } inline void write(longlong x) { if(x<0) putchar(‘-‘),x=-x; if(x>9) write(x/10); putchar(x%10+‘0‘); } long long n,m,k; long long head[100006],to[1000006],v[1000006],nxt[1000006]; long long total=0; long long dis[100006]; long long dis2[100006]; long long book[100006]; void add(long long x,long long y,long long z){ total++; to[total]=y; v[total]=z; nxt[total]=head[x]; head[x]=total; return ; } deque <long long> q; long long vis[100006]; void spfa_r(long long x){//SPFA板子 if(book[x]) return ; memset(dis,127,sizeof(dis)); memset(vis,0,sizeof(vis)); q.push_back(x); vis[x]=1; dis[x]=0; while(!q.empty()){ long long h=q.front(); q.pop_front(); vis[h]=0; for(long long e=head[h];e;e=nxt[e]){ if(book[to[e]]) continue; if(dis[to[e]]>dis[h]+v[e]){ dis[to[e]]=dis[h]+v[e]; if(!vis[to[e]]){ if(!q.empty()&&dis[to[e]]<=dis[q.front()]) q.push_front(to[e]); else q.push_back(to[e]); vis[to[e]]=1; } } } } return ; } void spfa_h(long long x){ memset(dis2,127,sizeof(dis2)); memset(vis,0,sizeof(vis)); q.push_back(x); vis[x]=1; dis2[x]=0; while(!q.empty()){ long long h=q.front(); q.pop_front(); vis[h]=0; for(long long e=head[h];e;e=nxt[e]){ if(dis2[to[e]]>dis2[h]+v[e]){ dis2[to[e]]=dis2[h]+v[e]; if(!vis[to[e]]){ if(!q.empty()&&dis2[to[e]]<=dis2[q.front()]) q.push_front(to[e]); else q.push_back(to[e]); vis[to[e]]=1; } } } } return ; } int main() { n=rd(),m=rd(),k=rd(); for(long long i=1;i<=k;i++){ long long x=rd(); book[x]=1; } for(long long i=1;i<=m;i++){ long long x=rd(),y=rd(),z=rd(); add(x,y,z); add(y,x,z); } long long l=rd(),r=rd(); spfa_r(1);//因為有的房間只有Harry能去 spfa_h(1);//所以要分開寫(滑稽) long long ans=min(max(dis2[l],dis[r]),max(dis2[r],dis[l]));//兩個人去的房間取最優(在這裏卡了半天) long long set=dis2[l]; long long sett=dis2[r]; spfa_h(l);//Harry先從l點開始 ans=min(ans,set+dis2[r]); spfa_h(r);//剛才把這行寫在了上面 ans=min(ans,sett+dis2[l]); printf("%lld",ans); return 0; }
NOIP2018原創模擬賽DAY1 密室