Submission #136924

#TimeUsernameProblemLanguageResultExecution timeMemory
136924popovicirobertValley (BOI19_valley)C++14
100 / 100
315 ms40184 KiB
#include <bits/stdc++.h>
#pragma GCC optimize ("Ofast")
#define lsb(x) (x & (-x))
#define ll long long
#define ull unsigned long long
// 217
// 44


/*const int MOD = 998244353;

inline int lgput(int a, int b) {
    int ans = 1;
    while(b > 0) {
        if(b & 1) ans = (1LL * ans * a) % MOD;
        b >>= 1;
        a = (1LL * a * a) % MOD;
    }
    return ans;
}

inline void mod(int &x) {
    if(x >= MOD)
        x -= MOD;
}

inline void add(int &x, int y) {
    x += y;
    mod(x);
}

inline void sub(int &x, int y) {
    x += MOD - y;
    mod(x);
}

inline void mul(int &x, int y) {
    x = (1LL * x * y) % MOD;
}*/

/*int fact[], invfact[];

inline void prec(int n) {
    fact[0] = 1;
    for(int i = 1; i <= n; i++) {
        fact[i] = (1LL * fact[i - 1] * i) % MOD;
    }
    invfact[n] = lgput(fact[n], MOD - 2);
    for(int i = n - 1; i >= 0; i--) {
        invfact[i] = (1LL * invfact[i + 1] * (i + 1)) % MOD;
    }
}

inline int comb(int n, int k) {
    if(n < k) return 0;
    return (1LL * fact[n] * (1LL * invfact[k] * invfact[n - k] % MOD)) % MOD;
}*/

using namespace std;

const ll INF = 1e18;
const int MAXN = (int) 1e5;

vector < pair <int, int> > g[MAXN + 1];

int anc[MAXN + 1][20];
ll best[MAXN + 1][20], down[MAXN + 1], dst[MAXN + 1];
bool shop[MAXN + 1];

int idl[MAXN + 1], idr[MAXN + 1], sz;
int lvl[MAXN + 1];

void dfs(int nod, int par) {
    idl[nod] = ++sz;
    lvl[nod] = lvl[par] + 1;
    down[nod] = (shop[nod] == 1 ? dst[nod] : INF);

    for(auto it : g[nod]) {
        if(it.first != par) {
            dst[it.first] = dst[nod] + it.second;
            dfs(it.first, nod);
            down[nod] = min(down[it.first], down[nod]);
        }
    }
    idr[nod] = sz;
}

void dfs1(int nod, int par) {
    anc[nod][0] = par;
    best[nod][0] = down[nod] - 2 * dst[nod];
    for(int bit = 1; bit < 20; bit++) {
        anc[nod][bit] = anc[anc[nod][bit - 1]][bit - 1];
        best[nod][bit] = min(best[nod][bit - 1], best[anc[nod][bit - 1]][bit - 1]);
    }

    for(auto it : g[nod]) {
        if(it.first != par) {
            dfs1(it.first, nod);
        }
    }
}

struct Edge {
    int a, b, c;
}edge[MAXN + 1];

int main() {
    //ifstream cin("A.in");
    //ofstream cout("A.out");
    int i, n, s, q, e;
    ios::sync_with_stdio(false);
    cin.tie(0), cout.tie(0);

    cin >> n >> s >> q >> e;

    for(i = 1; i < n; i++) {
        int a, b, c;
        cin >> a >> b >> c;
        edge[i] = {a, b, c};
        g[a].push_back({b, c});
        g[b].push_back({a, c});
    }

    while(s--) {
        int nod;
        cin >> nod;
        shop[nod] = 1;
    }

    dfs(e, 0);
    dfs1(e, 0);

    while(q--) {
        int pos, nod;
        cin >> pos >> nod;

        int a = edge[pos].a, b = edge[pos].b;
        if(lvl[a] > lvl[b]) {
            swap(a, b);
        }

        if(idl[b] <= idl[nod] && idr[nod] <= idr[b]) {
            ll ans = INF;
            int aux = nod;

            for(int bit = 19; bit >= 0; bit--) {
                if((lvl[nod] - lvl[b] + 1) & (1 << bit)) {
                    ans = min(ans, best[nod][bit]);
                    nod = anc[nod][bit];
                }
            }

            //cerr << best[3][0] << "\n";

            //cerr << a << " " << b << " " << ans << "\n";

            ans = min(ans + dst[aux], down[aux] - dst[aux]);

            if(ans < 1e15) {
                cout << ans << "\n";
            }
            else {
                cout << "oo\n";
            }
        }
        else {
            cout << "escaped\n";
        }
    }

    return 0;
}
#Verdict Execution timeMemoryGrader output
Fetching results...
#Verdict Execution timeMemoryGrader output
Fetching results...
#Verdict Execution timeMemoryGrader output
Fetching results...
#Verdict Execution timeMemoryGrader output
Fetching results...