1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98
| const int INF=0x3f3f3f3f; const int MAX=10000+10; int n,m,f[MAX],x,y,z,q,vis[MAX]; int fa[MAX],l[MAX],cost[MAX]; int anc[MAX][25],val[MAX][25]; int find(int x){ return f[x]==-1?x:f[x]=find(f[x]); } struct edge{ int x,y,c; bool operator< (const edge&x)const{ return c>x.c; } }e[MAX*5]; struct edge2{ int to,next,c; }ve[MAX*2]; int head[MAX],tot=0; void addedge(int u,int v,int c){ ve[tot].to=v; ve[tot].c=c; ve[tot].next=head[u]; head[u]=tot++; } void dfs(int u){ vis[u]=1; for(int i=head[u];i!=-1;i=ve[i].next){ int v=ve[i].to; if(vis[v]) continue; l[v]=l[u]+1; fa[v]=u; cost[v]=ve[i].c; dfs(v); } } void pre(){ mem(val,0x3f); fi(i,1,n+1){ anc[i][0]=fa[i];val[i][0]=cost[i]; for(int j=1;j<=20;j++)anc[i][j]=-1; } for(int j=1;j<=20;j++) fi(i,1,n+1) if(anc[i][j-1]!=-1){ int a=anc[i][j-1]; anc[i][j]=anc[a][j-1]; val[i][j]=min(val[i][j-1],val[a][j-1]); } } int lca(int p,int q){ if(find(p)!=find(q))return -1; if(l[p]<l[q]) swap(p,q); int ans=INF; for(int i=20;i>=0;i--) if(l[anc[p][i]]>=l[q]){ ans = min(ans,val[p][i]); p=anc[p][i]; } if(p==q) return ans; for(int i=20;i>=0;i--) if(anc[p][i]!=-1&&anc[p][i]!=anc[q][i]){ ans = min(ans,min(val[p][i],val[q][i])); p=anc[p][i];q=anc[q][i]; } return min(ans,min(val[p][0],val[q][0])); } int main(){ freopen("in","r",stdin); mem(f,-1);mem(fa,-1);mem(head,-1); sf(n);sf(m); fi(i,0,m){ sf(e[i].x);sf(e[i].y);sf(e[i].c); } sort(e,e+m); fi(i,0,m){ int u = find(e[i].x); int v = find(e[i].y); if(u!=v){ f[u]=v; addedge(e[i].x,e[i].y,e[i].c); addedge(e[i].y,e[i].x,e[i].c); } } fa[1]=-1; fi(i,1,n+1) if(!vis[i]){ l[i]=1; dfs(i); pre(); } sf(q); while(q--){ sf(x);sf(y); pf(lca(x,y));pfc("\n"); } return 0; }
|