Problem p02347 (C++)

Buggy submission (status: Memory Limit Exceeded):
#include <bits/stdc++.h>
#define rep(i, n) for (int i = 0; i < (n); i++)
using namespace std;
typedef pair<int, int> P;

vector<P> dat[10000000];
struct st {
  int a, b, c;
} p[500000];
bool operator<(st a, st b) { return P(a.a, a.b) < P(b.a, b.b); }
void init(int k, int l, int r) {
  if (r - l == 1) {
    dat[k].push_back(P(p[l].b, p[l].c));
    return;
  }
  int lb = k * 2 + 1, rb = k * 2 + 2;
  init(lb, l, (l + r) / 2);
  init(rb, (l + r) / 2, r);
  dat[k].resize(r - l);
  merge(dat[lb].begin(), dat[lb].end(), dat[rb].begin(), dat[rb].end(),
        dat[k].begin());
}
vector<int> query(int a, int b, int c, int d, int k, int l, int r) {
  if (b <= l || r <= a)
    return vector<int>();
  if (a <= l && r <= b) {
    int u = upper_bound(dat[k].begin(), dat[k].end(), P(d, INT_MAX)) -
            dat[k].begin();
    int v = upper_bound(dat[k].begin(), dat[k].end(), P(c, INT_MIN)) -
            dat[k].begin();
    vector<int> res;
    for (int i = v; i < u; i++)
      res.push_back(dat[k][i].second);
    return res;
  }
  auto lb = query(a, b, c, d, k * 2 + 1, l, (l + r) / 2);
  auto rb = query(a, b, c, d, k * 2 + 2, (l + r) / 2, r);
  for (int i : rb)
    lb.push_back(i);
  return lb;
}
int main() {
  int n;
  scanf("%d", &n);
  rep(i, n) scanf("%d%d", &p[i].a, &p[i].b), p[i].c = i;
  sort(p, p + n);
  init(0, 0, n);
  int q;
  scanf("%d", &q);
  rep(i, q) {
    int sx, tx, sy, ty;
    scanf("%d%d%d%d", &sx, &tx, &sy, &ty);
    int a = lower_bound(p, p + n, st{sx, INT_MIN, 0}) - p;
    int b = lower_bound(p, p + n, st{tx, INT_MAX, 0}) - p;
    auto res = query(a, b, sy, ty, 0, 0, n);
    sort(res.begin(), res.end());
    for (int j : res)
      printf("%d\n", j);
    puts("");
  }
}

Fixed submission:
#include <bits/stdc++.h>
#define rep(i, n) for (int i = 0; i < (n); i++)
using namespace std;
typedef pair<int, int> P;

vector<P> dat[2000000];
struct st {
  int a, b, c;
} p[500000];
bool operator<(st a, st b) { return P(a.a, a.b) < P(b.a, b.b); }
void init(int k, int l, int r) {
  if (r - l == 1) {
    dat[k].push_back(P(p[l].b, p[l].c));
    return;
  }
  int lb = k * 2 + 1, rb = k * 2 + 2;
  init(lb, l, (l + r) / 2);
  init(rb, (l + r) / 2, r);
  dat[k].resize(r - l);
  merge(dat[lb].begin(), dat[lb].end(), dat[rb].begin(), dat[rb].end(),
        dat[k].begin());
}
vector<int> query(int a, int b, int c, int d, int k, int l, int r) {
  if (b <= l || r <= a)
    return vector<int>();
  if (a <= l && r <= b) {
    int u = upper_bound(dat[k].begin(), dat[k].end(), P(d, INT_MAX)) -
            dat[k].begin();
    int v = upper_bound(dat[k].begin(), dat[k].end(), P(c, INT_MIN)) -
            dat[k].begin();
    vector<int> res;
    for (int i = v; i < u; i++)
      res.push_back(dat[k][i].second);
    return res;
  }
  auto lb = query(a, b, c, d, k * 2 + 1, l, (l + r) / 2);
  auto rb = query(a, b, c, d, k * 2 + 2, (l + r) / 2, r);
  for (int i : rb)
    lb.push_back(i);
  return lb;
}
int main() {
  int n;
  scanf("%d", &n);
  rep(i, n) scanf("%d%d", &p[i].a, &p[i].b), p[i].c = i;
  sort(p, p + n);
  init(0, 0, n);
  int q;
  scanf("%d", &q);
  rep(i, q) {
    int sx, tx, sy, ty;
    scanf("%d%d%d%d", &sx, &tx, &sy, &ty);
    int a = lower_bound(p, p + n, st{sx, INT_MIN, 0}) - p;
    int b = lower_bound(p, p + n, st{tx, INT_MAX, 0}) - p;
    auto res = query(a, b, sy, ty, 0, 0, n);
    sort(res.begin(), res.end());
    for (int j : res)
      printf("%d\n", j);
    puts("");
  }
}