Problem p03144 (C++)

Buggy submission (status: Runtime Error):
#include <bits/stdc++.h>
using namespace std;
typedef long long ll;
#define poly vector<ll>
#define sqr(x) ((x) * (x))
#define mp make_pair
inline char gc() {
  static char buf[100000], *p1 = buf, *p2 = buf;
  return p1 == p2 && (p2 = (p1 = buf) + fread(buf, 1, 100000, stdin), p1 == p2)
             ? EOF
             : *p1++;
}
#define gc getchar
inline ll read() {
  ll x = 0;
  char ch = gc();
  bool positive = 1;
  for (; !isdigit(ch); ch = gc())
    if (ch == '-')
      positive = 0;
  for (; isdigit(ch); ch = gc())
    x = x * 10 + ch - '0';
  return positive ? x : -x;
}
inline void write(ll a) {
  if (a < 0) {
    a = -a;
    putchar('-');
  }
  if (a >= 10)
    write(a / 10);
  putchar('0' + a % 10);
}
inline void wri(ll a) {
  write(a);
  putchar(' ');
}
inline void writeln(ll a) {
  write(a);
  puts("");
}
const int N = 200005;
const ll inf = 1e18;
vector<int> v[N];
poly me(poly a, poly b) {
  int n = a.size(), m = b.size(), i = 0, j = 0;
  poly c(n + m - 1);
  while (i < n && j < m) {
    c[i + j] = a[i] + b[j];
    if ((i + 1 < n && (j + 1 == m || a[i + 1] + b[j] > a[i] + b[j + 1])))
      i++;
    else
      j++;
  }
  return c;
}
poly operator+(poly a, poly b) {
  poly A[2], B[2];
  for (int i = 0; i < 2; i++) {
    for (unsigned j = i; j < a.size(); j += 2)
      A[i].push_back(a[j]);
    for (unsigned j = i; j < b.size(); j += 2)
      B[i].push_back(b[j]);
  }
  poly ans(a.size() + b.size() - 1);
  for (auto &i : ans)
    i = -inf;
  for (int i = 0; i < 2; i++) {
    for (int j = 0; j < 2; j++) {
      poly c = me(A[i], B[j]);
      for (unsigned k = 0; k < c.size(); k++) {
        ans[k * 2 + i + j] = max(ans[k * 2 + i + j], c[k]);
      }
    }
  }
  return ans;
}
poly solve(int l, int r) {
  if (l == r) {
    sort(v[l].begin(), v[l].end());
    int m = v[l].size();
    poly ans(m + 1);
    for (int i = 1; i <= m; i++)
      ans[i] = ans[i - 1] + v[l][m - i];
    ans[1] = -inf; // cout<<l<<" fjzzq "<<ans.size()<<endl;
    return ans;
  }
  int mid = (l + r) >> 1;
  return solve(l, mid) + solve(mid + 1, r);
}
signed main() {
  int n = read(), k = read();
  for (int i = 1; i <= n; i++) {
    int c = read(), w = read();
    v[c].push_back(w);
  }
  poly ans(n + 1);
  for (auto &i : ans)
    i = -inf;
  for (int i = 1; i <= 3; i++) {
    for (int i = 1; i <= k; i++)
      swap(v[i], v[(rand() << 15 ^ rand()) % i + 1]);
    poly zs = solve(1, k);
    for (int i = 1; i <= n; i++)
      ans[i] = max(ans[i], zs[i]);
  }
  for (int i = 1; i <= n; i++) {
    if (ans[i] < 0)
      puts("-1");
    else
      writeln(ans[i]);
  }
}


Fixed submission:
#include <bits/stdc++.h>
using namespace std;
typedef long long ll;
#define poly vector<ll>
#define sqr(x) ((x) * (x))
#define mp make_pair
inline char gc() {
  static char buf[100000], *p1 = buf, *p2 = buf;
  return p1 == p2 && (p2 = (p1 = buf) + fread(buf, 1, 100000, stdin), p1 == p2)
             ? EOF
             : *p1++;
}
#define gc getchar
inline ll read() {
  ll x = 0;
  char ch = gc();
  bool positive = 1;
  for (; !isdigit(ch); ch = gc())
    if (ch == '-')
      positive = 0;
  for (; isdigit(ch); ch = gc())
    x = x * 10 + ch - '0';
  return positive ? x : -x;
}
inline void write(ll a) {
  if (a < 0) {
    a = -a;
    putchar('-');
  }
  if (a >= 10)
    write(a / 10);
  putchar('0' + a % 10);
}
inline void wri(ll a) {
  write(a);
  putchar(' ');
}
inline void writeln(ll a) {
  write(a);
  puts("");
}
const int N = 200005;
const ll inf = 1e18;
vector<int> v[N];
poly me(poly a, poly b) {
  int n = a.size(), m = b.size(), i = 0, j = 0;
  poly c(n + m - 1);
  while (i < n && j < m) {
    c[i + j] = a[i] + b[j];
    if ((i + 1 < n && (j + 1 == m || a[i + 1] + b[j] > a[i] + b[j + 1])))
      i++;
    else
      j++;
  }
  return c;
}
poly operator+(poly a, poly b) {
  poly A[2], B[2];
  for (int i = 0; i < 2; i++) {
    for (unsigned j = i; j < a.size(); j += 2)
      A[i].push_back(a[j]);
    for (unsigned j = i; j < b.size(); j += 2)
      B[i].push_back(b[j]);
  }
  poly ans(a.size() + b.size() - 1);
  for (auto &i : ans)
    i = -inf;
  for (int i = 0; i < 2; i++) {
    for (int j = 0; j < 2; j++) {
      poly c = me(A[i], B[j]);
      for (unsigned k = 0; k < c.size(); k++) {
        ans[k * 2 + i + j] = max(ans[k * 2 + i + j], c[k]);
      }
    }
  }
  return ans;
}
poly solve(int l, int r) {
  if (l == r) {
    sort(v[l].begin(), v[l].end());
    int m = v[l].size();
    poly ans(m + 1);
    for (int i = 1; i <= m; i++)
      ans[i] = ans[i - 1] + v[l][m - i];
    ans[1] = -inf; // cout<<l<<" fjzzq "<<ans.size()<<endl;
    return ans;
  }
  int mid = (l + r) >> 1;
  return solve(l, mid) + solve(mid + 1, r);
}
signed main() {
  int n = read(), k = read();
  for (int i = 1; i <= n; i++) {
    int c = read(), w = read();
    v[c].push_back(w);
  }
  poly ans(n + 1);
  for (auto &i : ans)
    i = -inf;
  for (int i = 1; i <= 3; i++) {
    for (int i = 1; i <= k; i++)
      swap(v[i], v[((ll)rand() << 15 ^ rand()) % i + 1]);
    poly zs = solve(1, k);
    for (int i = 1; i <= n; i++)
      ans[i] = max(ans[i], zs[i]);
  }
  for (int i = 1; i <= n; i++) {
    if (ans[i] < 0)
      puts("-1");
    else
      writeln(ans[i]);
  }
}