[poj3114]Countries in War
2015-11-14 17:55
267 查看
传送门
http://poj.org/problem?id=3114题目大意
给出n个城市,m条边,如果从A能到B,从B也能到A,他们的通信时间为0. 求从s到t最短的通信时间。题解
先求scc,然后在scc上跑最短路我都换成离线处理了……无限TLE中QAQAQ
var dist,dfn,low,p,id:array[0..505]of longint; t:array[0..20000]of longint; z,w:array[0..5000,1..3]of longint; x:array[0..20000,1..4]of longint; i,j,k:longint; n,m,len,scc,a,b,c,q,tt,head,tail,v:longint; function min(a,b:longint):longint; begin if a>b then exit(b) else exit(a); end; procedure initz(a,b,c:longint); begin z[len,1]:=b; z[len,2]:=c; if z[a,3]=0 then z[a,3]:=len else z[z[a,1],3]:=len; z[a,1]:=len; inc(len); end; procedure initw(a,b,c:longint); begin w[len,1]:=b; w[len,2]:=c; if w[a,3]=0 then w[a,3]:=len else w[w[a,1],3]:=len; w[a,1]:=len; inc(len); end; procedure sort(l,r,vv:longint); var i,j,a,b:longint; begin i:=l; j:=r; a:=x[(l+r) div 2,vv]; repeat while x[i,vv]<a do inc(i); while a<x[j,vv] do dec(j); if not(i>j) then begin b:=x[i,1]; x[i,1]:=x[j,1]; x[j,1]:=b; b:=x[i,2]; x[i,2]:=x[j,2]; x[j,2]:=b; b:=x[i,3]; x[i,3]:=x[j,3]; x[j,3]:=b; b:=x[i,4]; x[i,4]:=x[j,4]; x[j,4]:=b; inc(i); dec(j); end; until i>j; if l<j then sort(l,j,vv); if i<r then sort(i,r,vv); end; procedure spfa(a:longint); var i:longint; begin for i:=1 to scc do dist[i]:=1000000; dist[a]:=0; head:=1; tail:=2; t[1]:=a; p[a]:=1; while head<tail do begin v:=t[head]; inc(head); tt:=w[v,3]; while tt<>0 do begin if dist[v]+w[tt,2]<dist[w[tt,1]] then begin dist[w[tt,1]]:=dist[v]+w[tt,2]; if p[w[tt,1]]=0 then begin p[w[tt,1]]:=1; t[tail]:=w[tt,1]; inc(tail); end; end; tt:=w[tt,3]; end; p[v]:=0; end; end; procedure tarjan(a:longint); var tt:longint; begin inc(len); dfn[a]:=len; low[a]:=len; inc(t[0]); t[t[0]]:=a; p[a]:=1; tt:=z[a,3]; while tt<>0 do begin if dfn[z[tt,1]]=0 then begin tarjan(z[tt,1]); low[a]:=min(low[z[tt,1]],low[a]); end else if p[z[tt,1]]=1 then low[a]:=min(dfn[z[tt,1]],low[a]); tt:=z[tt,3]; end; if dfn[a]=low[a] then begin inc(scc); repeat p[t[t[0]]]:=0; id[t[t[0]]]:=scc; dec(t[0]); until a=t[t[0]+1]; end; end; begin while not eof do begin readln(n,m); len:=n+1; if (n=0)and(m=0) then break; for i:=1 to m do begin readln(a,b,c); initz(a,b,c); end; z[0,1]:=len; len:=0; scc:=0; t[0]:=0; for i:=1 to n do if dfn[i]=0 then tarjan(i); len:=scc+1; for i:=1 to n do begin tt:=z[i,3]; while tt<>0 do begin if id[i]<>id[z[tt,1]] then initw(id[i],id[z[tt,1]],z[tt,2]); tt:=z[tt,3]; end; end; readln(q); for i:=1 to q do begin readln(a,b); x[i,1]:=id[a]; x[i,2]:=id[b]; x[i,3]:=i; end; sort(1,q,1); {x[i,1]} x[0,1]:=0; for i:=1 to q do begin if x[i,1]<>x[i-1,1] then spfa(x[i,1]); x[i,4]:=dist[x[i,2]]; end; sort(1,q,3); {x[i,3]} for i:=1 to q do if x[i,4]=1000000 then writeln('Nao e possivel entregar a carta') else writeln(x[i,4]); writeln; for i:=1 to n do for j:=1 to 3 do w[i,j]:=0; for i:=1 to n do for j:=1 to 3 do z[i,j]:=0; for i:=1 to n do begin dfn[i]:=0; low[i]:=0; end; end; end.
相关文章推荐
- NP完全性理论简介
- Bad Hair Day-POJ3250(简单的入栈出栈)
- ipython notebook [jupyter] 使用
- JQuery中$.ajax()方法参数详解
- MD5加密 C#窗体应用程序
- 集成学习——Boosting和Bagging
- 多线程的两种实现方式
- C#调用本机摄像头
- 下拉框选中 默认选中(从数据库比较,用户本身的值
- Unity3D内置运行函数
- 最长单调递增子数列
- 用户友好输入界面
- 使用AIDL实现进程间的通信
- Linux下安装Eclipse
- Oracle导入dmp备份文件到不同的表空间中
- 第32讲 实践项目——输出小星星5
- HDU 2795 Billboard 线段树单点更新
- Qt中的字符串类QString
- javascript利用FSO对XML文件操作类
- Oracle导入dmp备份文件到不同的表空间中