/ SeriousOJ /

Record Detail

Accepted


  
# Status Time Cost Memory Cost
#1 Accepted 6ms 15.633 MiB
#2 Accepted 7ms 16.027 MiB
#3 Accepted 6ms 16.062 MiB
#4 Accepted 7ms 15.746 MiB
#5 Accepted 7ms 15.789 MiB
#6 Accepted 6ms 16.105 MiB
#7 Accepted 15ms 16.246 MiB
#8 Accepted 16ms 15.996 MiB
#9 Accepted 17ms 16.004 MiB
#10 Accepted 17ms 16.312 MiB
#11 Accepted 237ms 19.863 MiB
#12 Accepted 229ms 19.941 MiB
#13 Accepted 232ms 19.898 MiB
#14 Accepted 245ms 19.906 MiB
#15 Accepted 130ms 16.934 MiB
#16 Accepted 124ms 17.168 MiB
#17 Accepted 124ms 16.77 MiB
#18 Accepted 128ms 16.879 MiB
#19 Accepted 127ms 16.812 MiB
#20 Accepted 125ms 16.973 MiB

Code

#include <iostream>
#include <vector>
#include <algorithm>
#include <cmath>
#include <cstring>

using namespace std;

const int MAXN = 100005;
const int LOG = 17; // log2(MAXN) + 1

vector<pair<int, int>> adj[MAXN];
int parent[MAXN][LOG], maxEdge[MAXN][LOG];
int depth[MAXN];

// DFS to initialize parent, maxEdge, and depth arrays
void dfs(int node, int par, int weight) {
    parent[node][0] = par;
    maxEdge[node][0] = weight;
    for (auto &[next, w] : adj[node]) {
        if (next != par) {
            depth[next] = depth[node] + 1;
            dfs(next, node, w);
        }
    }
}

// Binary Lifting Preprocessing
void preprocess(int n) {
    memset(parent, -1, sizeof(parent));
    memset(maxEdge, 0, sizeof(maxEdge));

    dfs(1, -1, 0); // Assuming node 1 is the root

    for (int j = 1; j < LOG; j++) {
        for (int i = 1; i <= n; i++) {
            if (parent[i][j - 1] != -1) {
                parent[i][j] = parent[parent[i][j - 1]][j - 1];
                maxEdge[i][j] = max(maxEdge[i][j - 1], maxEdge[parent[i][j - 1]][j - 1]);
            }
        }
    }
}

// Find LCA and maximum edge weight on the path between two nodes
int getMaxEdge(int u, int v) {
    if (depth[u] < depth[v]) swap(u, v);

    int maxWeight = 0;

    // Bring u and v to the same depth
    for (int i = LOG - 1; i >= 0; i--) {
        if (depth[u] - (1 << i) >= depth[v]) {
            maxWeight = max(maxWeight, maxEdge[u][i]);
            u = parent[u][i];
        }
    }

    if (u == v) return maxWeight;

    // Move both nodes up until they meet at LCA
    for (int i = LOG - 1; i >= 0; i--) {
        if (parent[u][i] != parent[v][i]) {
            maxWeight = max({maxWeight, maxEdge[u][i], maxEdge[v][i]});
            u = parent[u][i];
            v = parent[v][i];
        }
    }

    // Add the edge connecting to the LCA
    return max({maxWeight, maxEdge[u][0], maxEdge[v][0]});
}

int main() {
    int n, q;
    cin >> n >> q;

    for (int i = 0; i < n - 1; i++) {
        int u, v, w;
        cin >> u >> v >> w;
        adj[u].emplace_back(v, w);
        adj[v].emplace_back(u, w);
    }

    preprocess(n);

    while (q--) {
        int a, b;
        cin >> a >> b;
        cout << getMaxEdge(a, b) << "\n";
    }

    return 0;
}

Information

Submit By
Type
Submission
Problem
P1019 Graph Stuff
Language
C++17 (G++ 13.2.0)
Submit At
2024-12-07 14:14:50
Judged At
2024-12-07 14:14:50
Judged By
Score
100
Total Time
245ms
Peak Memory
19.941 MiB