Problem p02648 (C++) — buggy submission, verdict: Runtime Error

#include <bits/stdc++.h>
// #include <boost/multiprecision/cpp_int.hpp>
using namespace std;

#define all(a) (a).begin(), (a).end()
#define rall(a) (a).rbegin(), (a).rend()
#define MIN(a) *std::min_element((a).begin(), (a).end())
#define MAX(a) *std::max_element((a).begin(), (a).end())
#define SUM(a) std::accumulate((a).begin(), (a).end(), 0LL)
#define REP(i, n) for (std::size_t(i) = 0; (i) < (n); (i)++)
#define RREP(i, n) for (std::size_t(i) = (n)-1; (i) >= 0; (i)--)
#define FOR(i, m, n) for (std::size_t(i) = (m); (i) < (n); i++)
#define FORR(i, m, n) for (std::size_t(i) = (n)-1; (i) >= (m); i--)
#define debug(x) std::cerr << #x << " = " << x << '\\n'
// #define int long long

using ll = long long;
using ull = unsigned long long;
using ld = long double;
using vl = std::vector<long long>;
using vvl = std::vector<std::vector<long long>>;
// using bint = boost::multiprecision::cpp_int;
// using rat = boost::rational<bint>;

constexpr int inf = (1 << 30) - 1;
constexpr long long INF = 1LL << 60;

inline void ios_() {
  std::cin.tie(nullptr);
  std::ios::sync_with_stdio(false);
}
template <typename T> inline T Div(const T &a, const T &b) {
  return (a + b - 1) / b;
}
template <typename T> bool chmin(T &a, const T &b) {
  if (a > b) {
    a = b;
    return true;
  }
  return false;
}
template <typename T> bool chmax(T &a, const T &b) {
  if (a < b) {
    a = b;
    return true;
  }
  return false;
}

template <typename T> inline void finish(const T &msg) {
  std::cout << msg << std::endl;
  std::exit(0);
}

template <typename T>
long long binarySearch(long long ng, long long ok, const T &fn) {
  while (std::abs(ok - ng) > 1) {
    T mid = (ok + ng) / 2;
    if (fn(mid))
      ok = mid;
    else
      ng = mid;
  }
  return ok;
}

struct ModInt {
  long long value;
  static const long long mod; // mod must be a prime number

  ModInt(long long v = 0) : value(((v % mod) + mod) % mod) {}

  ModInt pow(long long n) const {
    long long x = value, res = 1;
    while (n > 0) {
      if (n & 1) {
        res = res * x % mod;
      }
      x = x * x % mod;
      n >>= 1;
    }
    return ModInt(res);
  }

  ModInt inverse() const { return pow(mod - 2); }

  ModInt operator-() const { return ModInt((mod - value) % mod); }

  ModInt &operator+=(const ModInt &a) {
    value += a.value;
    value %= mod;
    return *this;
  }

  ModInt &operator-=(const ModInt &a) {
    value += (-a).value;
    value %= mod;
    return *this;
  }

  ModInt &operator*=(const ModInt &a) {
    value *= a.value;
    value %= mod;
    return *this;
  }

  ModInt &operator/=(const ModInt &a) { return (*this) *= a.inverse(); }

  ModInt operator+(const ModInt &a) const { return ModInt(*this) += a; }

  ModInt operator-(const ModInt &a) const { return ModInt(*this) -= a; }

  ModInt operator*(const ModInt &a) const { return ModInt(*this) *= a; }

  ModInt operator/(const ModInt &a) const { return ModInt(*this) /= a; }

  bool operator==(const ModInt &a) const { return value == a.value; }

  bool operator!=(const ModInt &a) const { return value != a.value; }

  friend std::istream &operator>>(std::istream &is, ModInt &a) {
    long long v;
    is >> v;
    a = v;
    return is;
  }

  friend std::ostream &operator<<(std::ostream &os, const ModInt &a) {
    os << a.value;
    return os;
  }

  static ModInt factorial(int n) {
    static std::vector<ModInt> fact(1 << 18);
    if (fact.size() <= n) {
      fact.resize(n + 1);
    }
    if (n < 0) {
      return 0;
    }
    if (n == 0) {
      return 1;
    }
    if (fact[n] != 0) {
      return fact[n];
    }
    return fact[n] = factorial(n - 1) * n;
  }

  static ModInt combin(int n, int k) {
    if (n < 0 || k < 0 || n < k) {
      return 0;
    }
    return factorial(n) / (factorial(k) * factorial(n - k));
  }
};
const long long ModInt::mod = 1e9 + 7;
// const long long ModInt::mod = 998244353;
using mint = ModInt;

struct Solver {
  int n;
  int depth;
  vector<int> value;
  vector<int> weight;
  vector<vector<int>> dp;
  const int m = 100000;

  Solver() : depth(0) {
    int n;
    cin >> n;

    int x = n;
    while (x > 0) {
      depth++;
      x >>= 1;
    }

    value.resize((1 << depth) + 1, 0);
    weight.resize((1 << depth) + 1, 0);

    REP(i, n) { cin >> value[i + 1] >> weight[i + 1]; }

    dp = vector<vector<int>>(1 << (depth / 2), vector<int>(m + 1, -inf));
    dp[0][0] = 0;

    FOR(i, 1, 1 << (depth / 2)) {
      REP(j, m + 1) {
        chmax(dp[i][j], dp[i >> 1][j]);
        if (j + weight[i] <= m) {
          chmax(dp[i][j + weight[i]], dp[i >> 1][j] + value[i]);
        }
      }
    }

    REP(i, 1 << (depth / 2)) {
      REP(j, m) { chmax(dp[i][j + 1], dp[i][j]); }
    }
  }

  int rec(int x, int w) {
    if (w < 0)
      return -inf;
    if (x < (1 << (depth / 2))) {
      return dp[x][min(m, w)];
    }

    return max(rec(x >> 1, w), rec(x >> 1, w - weight[x]) + value[x]);
  }

  void solve() {
    int q;
    cin >> q;
    REP(i, q) {
      int v, w;
      cin >> v >> w;
      cout << rec(v, w) << '\\n';
    }
  }
};

signed main() {
  Solver S;
  S.solve();
  return 0;
}


Error: -6
terminate called after throwing an instance of 'std::bad_alloc'
  what():  std::bad_alloc


Fixed submission:

#include <bits/stdc++.h>
// #include <boost/multiprecision/cpp_int.hpp>
using namespace std;

#define all(a) (a).begin(), (a).end()
#define rall(a) (a).rbegin(), (a).rend()
#define MIN(a) *std::min_element((a).begin(), (a).end())
#define MAX(a) *std::max_element((a).begin(), (a).end())
#define SUM(a) std::accumulate((a).begin(), (a).end(), 0LL)
#define REP(i, n) for (std::size_t(i) = 0; (i) < (n); (i)++)
#define RREP(i, n) for (std::size_t(i) = (n)-1; (i) >= 0; (i)--)
#define FOR(i, m, n) for (std::size_t(i) = (m); (i) < (n); i++)
#define FORR(i, m, n) for (std::size_t(i) = (n)-1; (i) >= (m); i--)
#define debug(x) std::cerr << #x << " = " << x << '\\n'
// #define int long long

using ll = long long;
using ull = unsigned long long;
using ld = long double;
using vl = std::vector<long long>;
using vvl = std::vector<std::vector<long long>>;
// using bint = boost::multiprecision::cpp_int;
// using rat = boost::rational<bint>;

constexpr int inf = (1 << 30) - 1;
constexpr long long INF = 1LL << 60;

inline void ios_() {
  std::cin.tie(nullptr);
  std::ios::sync_with_stdio(false);
}
template <typename T> inline T Div(const T &a, const T &b) {
  return (a + b - 1) / b;
}
template <typename T> bool chmin(T &a, const T &b) {
  if (a > b) {
    a = b;
    return true;
  }
  return false;
}
template <typename T> bool chmax(T &a, const T &b) {
  if (a < b) {
    a = b;
    return true;
  }
  return false;
}

template <typename T> inline void finish(const T &msg) {
  std::cout << msg << std::endl;
  std::exit(0);
}

template <typename T>
long long binarySearch(long long ng, long long ok, const T &fn) {
  while (std::abs(ok - ng) > 1) {
    T mid = (ok + ng) / 2;
    if (fn(mid))
      ok = mid;
    else
      ng = mid;
  }
  return ok;
}

struct ModInt {
  long long value;
  static const long long mod; // mod must be a prime number

  ModInt(long long v = 0) : value(((v % mod) + mod) % mod) {}

  ModInt pow(long long n) const {
    long long x = value, res = 1;
    while (n > 0) {
      if (n & 1) {
        res = res * x % mod;
      }
      x = x * x % mod;
      n >>= 1;
    }
    return ModInt(res);
  }

  ModInt inverse() const { return pow(mod - 2); }

  ModInt operator-() const { return ModInt((mod - value) % mod); }

  ModInt &operator+=(const ModInt &a) {
    value += a.value;
    value %= mod;
    return *this;
  }

  ModInt &operator-=(const ModInt &a) {
    value += (-a).value;
    value %= mod;
    return *this;
  }

  ModInt &operator*=(const ModInt &a) {
    value *= a.value;
    value %= mod;
    return *this;
  }

  ModInt &operator/=(const ModInt &a) { return (*this) *= a.inverse(); }

  ModInt operator+(const ModInt &a) const { return ModInt(*this) += a; }

  ModInt operator-(const ModInt &a) const { return ModInt(*this) -= a; }

  ModInt operator*(const ModInt &a) const { return ModInt(*this) *= a; }

  ModInt operator/(const ModInt &a) const { return ModInt(*this) /= a; }

  bool operator==(const ModInt &a) const { return value == a.value; }

  bool operator!=(const ModInt &a) const { return value != a.value; }

  friend std::istream &operator>>(std::istream &is, ModInt &a) {
    long long v;
    is >> v;
    a = v;
    return is;
  }

  friend std::ostream &operator<<(std::ostream &os, const ModInt &a) {
    os << a.value;
    return os;
  }

  static ModInt factorial(int n) {
    static std::vector<ModInt> fact(1 << 18);
    if (fact.size() <= n) {
      fact.resize(n + 1);
    }
    if (n < 0) {
      return 0;
    }
    if (n == 0) {
      return 1;
    }
    if (fact[n] != 0) {
      return fact[n];
    }
    return fact[n] = factorial(n - 1) * n;
  }

  static ModInt combin(int n, int k) {
    if (n < 0 || k < 0 || n < k) {
      return 0;
    }
    return factorial(n) / (factorial(k) * factorial(n - k));
  }
};
const long long ModInt::mod = 1e9 + 7;
// const long long ModInt::mod = 998244353;
using mint = ModInt;

struct Solver {
  int n;
  int depth;
  vector<int> value;
  vector<int> weight;
  vector<vector<int>> dp;
  const int m = 100000;

  Solver() {
    int x;
    cin >> x;
    value.resize(x + 1);
    weight.resize(x + 1);
    REP(i, x) { cin >> value[i + 1] >> weight[i + 1]; }
    while (x > 0) {
      depth++;
      x >>= 1;
    }
    n = (1 << depth) - 1;

    value.resize(n + 1, 0);
    weight.resize(n + 1, 0);

    dp = vector<vector<int>>(1 << (depth / 2), vector<int>(m + 1, -inf));
    dp[0][0] = 0;

    FOR(i, 1, 1 << (depth / 2)) {
      REP(j, m + 1) {
        chmax(dp[i][j], dp[i >> 1][j]);
        if (j + weight[i] <= m) {
          chmax(dp[i][j + weight[i]], dp[i >> 1][j] + value[i]);
        }
      }
    }

    REP(i, 1 << (depth / 2)) {
      REP(j, m) { chmax(dp[i][j + 1], dp[i][j]); }
    }
  }

  ll rec(int x, int w) {
    if (w < 0)
      return 0;
    if (x < (1 << (depth / 2))) {
      return dp[x][min(m, w)];
    }

    return max(rec(x >> 1, w), rec(x >> 1, w - weight[x]) + value[x]);
  }

  void solve() {
    int q;
    cin >> q;
    REP(i, q) {
      int v, w;
      cin >> v >> w;
      cout << rec(v, w) << '\\n';
    }
  }
};

signed main() {
  Solver S;
  S.solve();
  return 0;
}