Source Code
#include<bits/stdc++.h>

using namespace std;
typedef long long ll;

#define FAST ios_base::sync_with_stdio(false); cin.tie(0); cout.tie(0);
#define mp make_pair
#define pb push_back
#define lp(i,s,f) for(ll i = s; i < ll(f); i++)
#define inF freopen("input.in", "r", stdin);
#define outF freopen("output.in", "w", stdout);
#define endl '\n'
#define MOD 1000000007
#define mm(arr) memset(arr, 0, sizeof(arr))
#define F first
#define S second

const long double PI = atan(1) * 4.0;

const int MAX_N = 2e5 + 1;
const int LOG = 22;
vector<int> adj[MAX_N];
int up[MAX_N][LOG]; // up[v][j] is 2^j-th ancestor of v
int depth[MAX_N];
int n;
void dfs(int a) {
    for(int b : adj[a]) {
        depth[b] = depth[a] + 1;
        up[b][0] = a; // a is parent of b
        for(int j = 1; j < LOG; j++) {
            up[b][j] = up[up[b][j-1]][j-1];
        }
        dfs(b);
    }
}

int get_lca(int a, int b) { // O(log(N))
    if(depth[a] < depth[b]) {
        swap(a, b);
    }
    // 1) Get same depth.
    int k = depth[a] - depth[b];
    for(int j = LOG - 1; j >= 0; j--) {
        if(k & (1 << j)) {
            a = up[a][j]; // parent of a
        }
    }
    // 2) if b was ancestor of a then now a==b
    if(a == b) {
        return a;
    }
    // 3) move both a and b with powers of two
    for(int j = LOG - 1; j >= 0; j--) {
        if(up[a][j] != up[b][j]) {
            a = up[a][j];
            b = up[b][j];
        }
    }
    return up[a][0];
}

int main(){
    FAST
    cin >> n;
    for(int i = 1; i < n; i++){
        int p; cin >> p;
        p--;
        adj[p].pb(i);
    }
    dfs(0);
    int val[n];
    for(int i = 0; i < n; i++){
        cin >> val[i];
    }
    vector<int> options[n];
    for(int i = 0; i < n; i++){
        if(depth[i] >= 4)
            options[up[i][2]].pb(i);
    }
    for(int i = 0; i < n; i++){
        int mn = 2e9;
        int curr = 1e9;
        for(int j = 0; j < options[i].size(); j++){
            if(mn > abs(val[i] - val[options[i][j]])){
                curr = options[i][j] + 1;
                mn = abs(val[i] - val[options[i][j]]);
            }
            else if(mn == abs(val[i] - val[options[i][j]])){
                if(curr > options[i][j] + 1){
                    curr = options[i][j] + 1;
                }
            }
        }
        if(curr == 1e9){
            curr = 0;
        }
        cout << curr << " ";
    }
    return 0;
}

Copy
Find a Friend Basilhijaz
GNU G++17
200 ms
46.4 MB
Accepted