Problem p03941 (C++)

Buggy submission (status: Runtime Error):
// Love and Freedom.
#include <algorithm>
#include <cmath>
#include <cstdio>
#include <cstring>
#include <vector>
#define ll long long
#define inf 20021225
#define pa pair<ll, ll>
#define mp make_pair
#define fs first
#define se second
#define N 131072
#define pb push_back
#define ls(x) son[x][0]
#define rs(x) son[x][1]
using namespace std;
int read() {
  int s = 0, f = 1;
  char ch = getchar();
  while (ch < '0' || ch > '9') {
    if (ch == '-')
      f = -1;
    ch = getchar();
  }
  while (ch >= '0' && ch <= '9')
    s = s * 10 + ch - '0', ch = getchar();
  return f * s;
}
vector<int> son[N + 2];
int val[N + 2];
vector<pa> f[N + 2], tmp[2];
ll mid;
void dfs(int x) {
  f[x].clear();
  if (!son[x].size()) {
    f[x].pb(mp(0, 0));
    return;
  }
  dfs(ls(x));
  dfs(rs(x));
  for (int p = 0; p < 2; p++) {
    tmp[p].clear();
    int a = son[x][p], b = son[x][p ^ 1];
    int r = 0;
    for (int i = 0; i < f[a].size(); i++) {
      while (r < f[b].size() - 1 &&
             f[b][r + 1].fs + f[a][i].se + val[a] + val[b] <= mid)
        r++;
      if (r < f[b].size() && f[b][r].fs + f[a][i].se + val[a] + val[b] <= mid)
        tmp[p].pb(mp(f[a][i].fs + val[a], f[b][r].se + val[b]));
    }
  }
  int i = 0, j = 0;
  ll cur = 1e18;
  while (i < tmp[0].size() && j < tmp[1].size()) {
    if (tmp[0][i] < tmp[1][j]) {
      if (tmp[0][i].se < cur)
        f[x].pb(tmp[0][i]), cur = tmp[0][i].se;
      i++;
    } else {
      if (tmp[1][j].se < cur)
        f[x].pb(tmp[1][j]), cur = tmp[1][j].se;
      j++;
    }
  }
  while (i < tmp[0].size()) {
    if (tmp[0][i].se < cur)
      f[x].pb(tmp[0][i]), cur = tmp[0][i].se;
    i++;
  }
  while (j < tmp[1].size()) {
    if (tmp[1][j].se < cur)
      f[x].pb(tmp[1][j]), cur = tmp[1][j].se;
    j++;
  }
}
bool check() {
  dfs(1);
  if (f[1].size())
    return 1;
  return 0;
}
int main() {
  int n = read();
  ll l = 0, r = 0;
  for (int i = 2; i <= n; i++) {
    int fa = read();
    val[i] = read();
    son[fa].pb(i);
    r += val[i];
  }
  ll ans = r;
  while (l <= r) {
    mid = l + r >> 1;
    if (check())
      ans = mid, r = mid - 1;
    else
      l = mid + 1;
  }
  printf("%lld\n", ans);
  return 0;
}

Fixed submission:
// Love and Freedom.
#include <algorithm>
#include <cmath>
#include <cstdio>
#include <cstring>
#include <vector>
#define ll long long
#define inf 20021225
#define pa pair<ll, ll>
#define mp make_pair
#define fs first
#define se second
#define N 131072
#define pb push_back
#define ls(x) son[x][0]
#define rs(x) son[x][1]
using namespace std;
int read() {
  int s = 0, f = 1;
  char ch = getchar();
  while (ch < '0' || ch > '9') {
    if (ch == '-')
      f = -1;
    ch = getchar();
  }
  while (ch >= '0' && ch <= '9')
    s = s * 10 + ch - '0', ch = getchar();
  return f * s;
}
vector<int> son[N + 2];
int val[N + 2];
vector<pa> f[N + 2], tmp[2];
ll mid;
void dfs(int x) {
  f[x].clear();
  if (!son[x].size()) {
    f[x].pb(mp(0, 0));
    return;
  }
  dfs(ls(x));
  dfs(rs(x));
  for (int p = 0; p < 2; p++) {
    tmp[p].clear();
    int a = son[x][p], b = son[x][p ^ 1];
    int r = 0;
    for (int i = 0; i < f[a].size(); i++) {
      while (r + 1 < f[b].size() &&
             f[b][r + 1].fs + f[a][i].se + val[a] + val[b] <= mid)
        r++;
      if (r < f[b].size() && f[b][r].fs + f[a][i].se + val[a] + val[b] <= mid)
        tmp[p].pb(mp(f[a][i].fs + val[a], f[b][r].se + val[b]));
    }
  }
  int i = 0, j = 0;
  ll cur = 1e18;
  while (i < tmp[0].size() && j < tmp[1].size()) {
    if (tmp[0][i] < tmp[1][j]) {
      if (tmp[0][i].se < cur)
        f[x].pb(tmp[0][i]), cur = tmp[0][i].se;
      i++;
    } else {
      if (tmp[1][j].se < cur)
        f[x].pb(tmp[1][j]), cur = tmp[1][j].se;
      j++;
    }
  }
  while (i < tmp[0].size()) {
    if (tmp[0][i].se < cur)
      f[x].pb(tmp[0][i]), cur = tmp[0][i].se;
    i++;
  }
  while (j < tmp[1].size()) {
    if (tmp[1][j].se < cur)
      f[x].pb(tmp[1][j]), cur = tmp[1][j].se;
    j++;
  }
}
bool check() {
  dfs(1);
  if (f[1].size())
    return 1;
  return 0;
}
int main() {
  int n = read();
  ll l = 0, r = 0;
  for (int i = 2; i <= n; i++) {
    int fa = read();
    val[i] = read();
    son[fa].pb(i);
    r += val[i];
  }
  ll ans = r;
  while (l <= r) {
    mid = l + r >> 1;
    if (check())
      ans = mid, r = mid - 1;
    else
      l = mid + 1;
  }
  printf("%lld\n", ans);
  return 0;
}