kruskal+倍增0分求调
查看原帖
kruskal+倍增0分求调
668379
Poole_tea楼主2024/12/27 20:25

rt

#include <bits/stdc++.h>
using namespace std ;
const int MAXN = 5e4 + 10 ;
struct edge {
    int x, y, w ;
}e[MAXN] ;
struct node {
    int to, w ;
} ;
vector<node> g[MAXN] ;
inline bool cmp (edge a, edge b) {
    return a.w > b.w ;
}
int fa[MAXN], dep[MAXN], f[MAXN][25], val[MAXN], k[MAXN][25] ;
inline int find (int x) {
    if (x == fa[x]) return x ;
    return fa[x] = find(fa[x]) ;
}
inline void dfs (int x, int fa) {
    for (auto i : g[x]) {
        int v = i.to ;
        if (v == fa) continue ;
        dep[v] = dep[x] + 1 ;
        val[v] = i.w ;
        k[v][0] = x ;
        f[v][0] = i.w ;
        dfs(v, x) ;
    }
}
inline int query (int x, int y) {
	if (find(x) != find(y)) return -1 ;
    if (dep[x] < dep[y]) swap(x, y) ;
    int ans = 1000000007 ;
    for (int i = 20 ; i >= 0 ; i--) {
        if (dep[k[x][i]] >= dep[y]) {
		    ans = min (ans, f[x][i]) ;
            x = k[x][i] ;
        }
    }
    if (x == y) return ans ;
    for (int i = 20 ; i >= 0 ; i--) {
        if (k[x][i] != k[y][i]) {
            ans = min (ans, f[x][i]) ;
            ans = min (ans, f[y][i]) ;
            x = k[x][i] ;
            y = k[y][i] ;
        }
    }
    ans = min(ans, min(f[x][0], f[y][0])) ;
    return ans ;
}
int main () {
    int n, m ;
    cin >> n >> m ;
    for (int i = 1 ; i <= m ; i++) cin >> e[i].x >> e[i].y >> e[i].w ;
    sort(e + 1, e + m + 1, cmp) ;
    int tot = 0, sum = 0 ;
    for (int i = 1 ; i <= n ; i++) fa[i] = i ;
    for (int i = 1 ; i <= m ; i++) {
        int x = find(e[i].x), y = find(e[i].y) ;
        if (x == y) continue ;
        fa[x] = y ;
        g[e[i].x].push_back({e[i].y, e[i].w}) ;
        g[e[i].y].push_back({e[i].x, e[i].w}) ;
        sum += e[i].w ;
        if (++tot == n - 1) break ;
    }
    for (int i = 1 ; i <= MAXN ; i++) 
		for (int j = 1 ; j <= 20 ; j++) f[i][j] = 1000000007 ;
    dep[1] = 1 ;
    dfs(1, 0) ; 
    for (int j = 1 ; j <= 20 ; j++) {
        for (int i = 1 ; i <= n ; i++) f[i][j] = min(f[i][j - 1], f[f[i][j - 1]][j - 1]) ;
    }
    for (int j = 1 ; j <= 20 ; j++) {
        for (int i = 1 ; i <= n ; i++) k[i][j] = k[k[i][j - 1]][j - 1] ;
    }
    int q, x, y ;
    cin >> q ;
    while (q--) {
        cin >> x >> y ;
        cout << query(x, y) << '\n' ;
    }
    return 0 ;
}
2024/12/27 20:25
加载中...