bzoj2725: [Violet 6]故乡的梦

Description

Input

Output

Sample Input

6 7
1 2 1
2 3 1
3 4 2
4 5 1
5 6 1
1 3 3
4 6 3
1 6
4
1 2
1 3
4 3
6 5

Sample Output


7
6
Infinity
7

HINT

 
题解:
这和tjoi的桥几乎无差别。。。
传送门:http://www.cnblogs.com/chenyushuo/p/5121234.html
补:此题样例有误,答案为5其实是6
code:
  1 #include<cstdio>
  2 #include<iostream>
  3 #include<cmath>
  4 #include<cstring>
  5 #include<algorithm>
  6 #define maxn 200005
  7 #define maxm 400005
  8 #define mod 236897
  9 #define inf 4557430888798830399LL
 10 using namespace std;
 11 typedef long long int64;
 12 char ch;
 13 bool ok;
 14 void read(int &x){
 15     for (ok=0,ch=getchar();!isdigit(ch);ch=getchar()) if (ch=='-') ok=1;
 16     for (x=0;isdigit(ch);x=x*10+ch-'0',ch=getchar());
 17     if (ok) x=-x;
 18 }
 19 int n,m,q,a,b,s,t,u[maxm],v[maxm],c[maxm];
 20 int tot=1,now[maxn],son[maxm],pre[maxm],val[maxm];
 21 void put(int a,int b,int c){pre[++tot]=now[a],now[a]=tot,son[tot]=b,val[tot]=c;}
 22 int siz,pos[maxn],path[maxn];
 23 int64 dis[maxn][2];
 24 bool bo[maxn],flag[maxm];
 25 struct Heap{
 26     int num;
 27     int64 val;
 28 }heap[maxn];
 29 void heap_swap(Heap &a,Heap &b){swap(pos[a.num],pos[b.num]),swap(a,b);}
 30 void up(int son){
 31     int fa=son>>1;
 32     while (fa){
 33         if (heap[fa].val<=heap[son].val) break;
 34         heap_swap(heap[fa],heap[son]);
 35         son=fa,fa>>=1;
 36     }
 37 }
 38 void down(){
 39     int fa=1,son=fa<<1;
 40     while (son<=siz){
 41         if (son+1<=siz&&heap[son+1].val<heap[son].val) son++;
 42         if (heap[fa].val<=heap[son].val) break;
 43         heap_swap(heap[fa],heap[son]);
 44         fa=son,son<<=1;
 45     }
 46 }
 47 void dijkstra(int s,int op){
 48     memset(bo,0,sizeof(bo));
 49     memset(pos,0,sizeof(pos));
 50     siz=0;
 51     heap[++siz]=(Heap){s,0},pos[s]=siz;
 52     for (;siz;){
 53         int u=heap[1].num;
 54         int64 d=heap[1].val;
 55         bo[u]=1,dis[u][op]=d,heap_swap(heap[1],heap[siz--]),down();
 56         for (int p=now[u],v=son[p];p;p=pre[p],v=son[p])
 57             if (!bo[v]){
 58                 if (!pos[v]){
 59                     heap[++siz]=(Heap){v,d+val[p]},pos[v]=siz,up(pos[v]);
 60                     if (!op) path[v]=p;
 61                 }
 62                 else if (heap[pos[v]].val>d+val[p]){
 63                     heap[pos[v]].val=d+val[p],up(pos[v]);
 64                     if (!op) path[v]=p;
 65                 }
 66             }
 67     }
 68 }
 69 int cnt,tmp[maxn],list[maxn],dep[maxn];
 70 void prepare(){
 71     for (int u=t;u;u=son[path[u]^1]) tmp[++cnt]=u;
 72     for (int i=1;i<=cnt;i++) list[cnt-i+1]=tmp[i];
 73     for (int i=1;i<=cnt;i++) dep[list[i]]=i;
 74     for (int i=1;i<=n;i++) if (!dep[i]){
 75         int u=i,d=0;
 76         while (!dep[u]) u=son[path[u]^1];
 77         d=dep[u],u=i;
 78         while (!dep[u]) dep[u]=d,u=son[path[u]^1];
 79     }
 80     for (int u=1;u<=n;u++) if (path[u]) flag[path[u]>>1]=1;
 81 }
 82 int64 dam[maxn];
 83 struct seg{
 84     #define ls k<<1
 85     #define rs (k<<1)+1
 86     int64 cov[maxn<<2];
 87     void init(){memset(cov,63,sizeof(cov));}
 88     void modify(int k,int l,int r,int x,int y,int64 v){
 89         if (l==x&&r==y){cov[k]=min(cov[k],v);return;}
 90         int m=(l+r)>>1;
 91         if (y<=m) modify(ls,l,m,x,y,v);
 92         else if (x<=m) modify(ls,l,m,x,m,v),modify(rs,m+1,r,m+1,y,v);
 93         else modify(rs,m+1,r,x,y,v);
 94     }
 95     void query(int k,int l,int r,int64 ans){
 96         ans=min(ans,cov[k]);
 97         if (l==r){dam[l]=ans;return;}
 98         int m=(l+r)>>1;
 99         query(ls,l,m,ans),query(rs,m+1,r,ans);
100     }
101 }T;
102 void work(int u,int v,int c){
103     if (dep[u]==dep[v]) return;
104     if (dep[u]>dep[v]) swap(u,v);
105     T.modify(1,1,cnt-1,dep[u],dep[v]-1,dis[u][0]+c+dis[v][1]);
106 }
107 int main(){
108     read(n),read(m);
109     for (int i=1;i<=m;i++) read(u[i]),read(v[i]),read(c[i]),put(u[i],v[i],c[i]),put(v[i],u[i],c[i]);
110     read(s),read(t);
111     dijkstra(s,0),dijkstra(t,1);
112     prepare(),T.init();
113     for (int i=1;i<=m;i++) if (!flag[i]) work(u[i],v[i],c[i]);
114     T.query(1,1,cnt-1,inf);
115     for (read(q);q;q--){
116         read(a),read(b);
117         if (dis[a][0]>dis[b][0]) swap(a,b);
118         if (dep[a]+1==dep[b]&&son[path[b]^1]==a){
119             if (dam[dep[a]]!=inf) printf("%lld
",dam[dep[a]]);
120             else puts("Infinity");
121         }
122         else{
123             if (dis[t][0]!=inf) printf("%lld
",dis[t][0]);
124             else puts("Infinity");
125         }
126     }
127     return 0;
128 }
原文地址:https://www.cnblogs.com/chenyushuo/p/5121250.html