题目链接:点这里
题解:这道算是一道蛮有意思的题,这道题我们要用最小生成树+lca来写。我们贪心的想,我们要使这条路上的最小的最大。我们可以建一个最小生成树,但是我们排序的时候要把边权较大的放在最前面,然后用krustal来建这个树即可。建完树以后,我们可以用lca来解决询问问题。每当询问的时候,我们可以用lca来找他们的公共祖先,然后再取这两条路上的最小值就可以了。
#include<bits/stdc++.h>
#define ll long long
#define pr pair<ll,ll>
#define ios ios::sync_with_stdio(false)
#define CRL(a) memset(a,0,sizeof a)
#define endl "\n"
using namespace std;
const int maxn = 1e5 + 5;
struct node
{
int u, v, w;
} e[maxn];
struct node1
{
int to, next, w;
} e1[maxn];
bool vis[maxn];
int ff[maxn];
int cnt = 1;
int head[maxn];
int d[maxn];
int dist[maxn][25];
int f[maxn][25];
int t;
bool cmp(node a,node b)
{
return a.w > b.w;
}
int find(int a)
{
if(a==ff[a])
return ff[a];
return ff[a] = find(ff[a]);
}
void add(int u,int v,int w)
{
e1[cnt] = {v, head[u], w};
head[u] = cnt++;
}
void bfs()
{
queue<int> q;
q.push(1);
d[1] = 1;
dist[1][0] = 1e9 + 5;
while(q.size())
{
int a = q.front();
q.pop();
for (int i = head[a]; i;i=e1[i].next)
{
int v = e1[i].to, w = e1[i].w;
if(d[v])
continue;
d[v] = d[a] + 1;
dist[v][0] = w;
f[v][0] = a;
for (int j = 1; j <= t;j++)
{
f[v][j] = f[f[v][j - 1]][j - 1];
dist[v][j] = min(dist[v][j - 1], dist[f[v][j - 1]][j - 1]);
}
q.push(v);
}
}
}
int lca(int x,int y)
{
if(find(x)!=find(y))
return -1;
if(d[x]>d[y])
swap(x, y);
int ans = 1e9 + 5;
for (int i = t; i >= 0;i--)
{
if(d[f[y][i]]>=d[x])
ans = min(ans, dist[y][i]), y = f[y][i];
}
if(x==y)
return ans;
for (int i = t; i >= 0;i--)
{
if(f[x][i]!=f[y][i])
{
ans = min(ans, min(dist[y][i], dist[x][i]));
x = f[x][i], y = f[y][i];
}
}
ans = min(ans, min(dist[x][0], dist[y][0]));
return ans;
}
int main()
{
int n,m;
cin >> n >> m;
t = 20;
for (int i = 1; i <= n;i++)
ff[i] = i;
for (int i = 1; i <= m; i++)
{
cin >> e[i].u >> e[i].v >> e[i].w;
}
sort(e + 1, e + 1 + m, cmp);
int ans = 0;
for (int i = 1; i <= m;i++)
{
int u = e[i].u, v = e[i].v;
u = find(u), v = find(v);
if(u!=v)
{
ff[u] = v;
add(e[i].u, e[i].v, e[i].w);
add(e[i].v, e[i].u, e[i].w);
// cout << e[i].u << e[i].v << endl;
}
}
bfs();
//cout << f[3][1] << endl;
int tt;
cin >> tt;
while(tt--)
{
int a, b;
cin >> a >> b;
cout << lca(a, b) << endl;
}
}