【题目链接】
http://www.lydsy.com/JudgeOnline/problem.php?id=3732
【题意】
给定一个无向图,处理若干询问:uv路径上最长的边最小是多少?
【思路一】
最小生成树+倍增算法。
同NOIP2013货车运输。
【代码】
1 #include<set> 2 #include<cmath> 3 #include<queue> 4 #include<vector> 5 #include<cstdio> 6 #include<cstring> 7 #include<iostream> 8 #include<algorithm> 9 #define trav(u,i) for(int i=front[u];i;i=e[i].nxt) 10 #define FOR(a,b,c) for(int a=(b);a<=(c);a++) 11 using namespace std; 12 13 typedef long long ll; 14 const int N = 1e5+10; 15 const int M = 2e5+10; 16 const int D = 21; 17 const int inf = 2e9; 18 19 ll read() { 20 char c=getchar(); 21 ll f=1,x=0; 22 while(!isdigit(c)) { 23 if(c=='-') f=-1; c=getchar(); 24 } 25 while(isdigit(c)) 26 x=x*10+c-'0',c=getchar(); 27 return x*f; 28 } 29 30 struct Edge { 31 int u,v,w,nxt; 32 bool operator < (const Edge& rhs) const{ 33 return w<rhs.w; 34 } 35 }e[M]; 36 int en=1,front[N]; 37 void adde(int u,int v,int w) 38 { 39 e[++en]=(Edge){u,v,w,front[u]}; front[u]=en; 40 } 41 vector<Edge> es; 42 43 int n,m,K,p[N],_max[N][D],fa[N][D],dep[N]; 44 45 int ifind(int u) 46 { 47 return u==p[u]? u:p[u]=ifind(p[u]); 48 } 49 50 void Kruskal() 51 { 52 sort(es.begin(),es.end()); 53 FOR(i,0,(int)es.size()-1) { 54 int u=es[i].u,v=es[i].v,w=es[i].w; 55 int x=ifind(u),y=ifind(v); 56 if(x!=y) { 57 p[x]=y; 58 adde(u,v,w); adde(v,u,w); 59 } 60 } 61 } 62 void dfs(int u,int father) 63 { 64 trav(u,i) { 65 int v=e[i].v; 66 if(v!=father) { 67 fa[v][0]=u; 68 _max[v][0]=e[i].w; 69 dep[v]=dep[u]+1; 70 FOR(j,1,D-1) { 71 fa[v][j]=fa[fa[v][j-1]][j-1]; 72 _max[v][j]=max(_max[v][j-1],_max[fa[v][j-1]][j-1]); 73 } 74 dfs(v,u); 75 } 76 } 77 } 78 79 int query(int u,int v) 80 { 81 if(dep[u]<dep[v]) swap(u,v); 82 int t=dep[u]-dep[v],ans=-inf; 83 FOR(i,0,D-1) 84 if(t&(1<<i)) { 85 ans=max(ans,_max[u][i]); 86 u=fa[u][i]; 87 } 88 if(u==v) return ans; 89 for(int i=D-1;i>=0;i--) 90 if(fa[u][i]!=fa[v][i]) { 91 ans=max(ans,max(_max[u][i],_max[v][i])); 92 u=fa[u][i],v=fa[v][i]; 93 } 94 ans=max(ans,max(_max[u][0],_max[v][0])); 95 return ans; 96 } 97 98 int main() 99 { 100 n=read(),m=read(),K=read(); 101 FOR(i,0,n) FOR(j,0,D-1) _max[i][j]=-inf; 102 FOR(i,1,n) p[i]=i; 103 FOR(i,1,m) { 104 int u=read(),v=read(),w=read(); 105 es.push_back((Edge){u,v,w,0}); 106 } 107 Kruskal(); 108 dfs(1,-1); 109 FOR(i,1,K) { 110 int u=read(),v=read(); 111 printf("%d\n",query(u,v)); 112 } 113 return 0; 114 }