Problem p02599 (C++) — buggy submission, verdict: Time Limit Exceeded

#include <algorithm>
#include <iostream>
#include <map>
#include <set>
#include <string>
#include <vector>

using namespace std;

int N, Q;
int c[500005];
int l[500005], r[500005];

int ans[500005];
vector<int> Vl[500005], Vi[500005];

int Data[1 << 21], Datb[1 << 21];

int M = 1 << 19;

void ADD(int a, int b, int l, int r, int k, int x) { // call l=0, r=M-1, k=1

  if (b < l || r < a) {
    return;
  }

  if (a <= l && r <= b) {
    Data[k] += x;
  } else {
    Datb[k] += (min(b, r) - max(a, l) + 1) * x;

    ADD(a, b, l, (l + r) / 2, 2 * k, x);
    ADD(a, b, (l + r) / 2 + 1, r, 2 * k + 1, x);
  }
}

int SUM(int a, int b, int l, int r, int k) { // call l=0, r=M-1, k=0
  int ret = 0;

  if (b < l || r < a) {
    return 0;
  }

  if (a <= l && r <= b) {
    return Data[k] * (r - l + 1) + Datb[k];
  } else {
    ret += Data[k] * (min(b, r) - max(l, a) + 1);
    ret += SUM(a, b, l, (l + r) / 2, k * 2);
    ret += SUM(a, b, (l + r) / 2 + 1, r, 2 * k + 1);
  }
  return ret;
}

int pre_pos[500005];

int last[500005];

int main(void) {

  cin >> N >> Q;
  for (int i = 1; i <= N; i++) {
    cin >> c[i];
  }
  for (int i = 1; i <= Q; i++) {
    cin >> l[i] >> r[i];
  }

  for (int i = 1; i <= N; i++) {
    pre_pos[i] = last[c[i]];
    last[c[i]] = i;
  }

  /*for (int i = 1; i <= N; i++) {
          cout << "pre_pos[" << i << "]= " << pre_pos[i] << endl;
  }*/

  for (int i = 1; i <= Q; i++) {
    Vl[r[i]].push_back(l[i]);
    Vi[r[i]].push_back(i);
  }

  for (int i = 1; i <= N; i++) {
    int p = pre_pos[i];
    // cout << "pre_pos[" << i << "]= " << pre_pos[i] << endl;
    ADD(p + 1, i, 0, M - 1, 1, 1);
    for (int u = 0; u < (int)Vl[i].size(); u++) {
      int num = SUM(Vl[i][u], Vl[i][u], 0, M - 1, 1);
      ans[Vi[i][u]] = num;
    }
  }

  for (int i = 1; i <= Q; i++) {
    cout << ans[i] << endl;
  }

  /*ADD(0, 3, 0, M - 1, 1, 7);
  ADD(3, 5, 0, M - 1, 1, 9);
  ADD(6, 7, 0, M - 1, 1, 20);

  for (int k = 1; k <= 16; k++) {

          cout << "Data[" << k << "]= " << Data[k] <<"  Datb["<<k<<"]= "<<
  Datb[k] << endl;
  }

  cout << "SUM= " << SUM(6, 7, 0, M - 1, 1) << endl;
  */

  return 0;
}

Error: TLE

Fixed submission:

#include <algorithm>
#include <iostream>
#include <map>
#include <set>
#include <string>
#include <vector>

using namespace std;

int N, Q;
int c[500005];
int l[500005], r[500005];

vector<int> V[500005];

int Data[1 << 21], Datb[1 << 21];

int M = 1 << 19;

map<pair<int, int>, int> ans;

void ADD(int a, int b, int l, int r, int k, int x) { // call l=0, r=M-1, k=1

  if (b < l || r < a) {
    return;
  }

  if (a <= l && r <= b) {
    Data[k] += x;
  } else {
    Datb[k] += (min(b, r) - max(a, l) + 1) * x;

    ADD(a, b, l, (l + r) / 2, 2 * k, x);
    ADD(a, b, (l + r) / 2 + 1, r, 2 * k + 1, x);
  }
}

int SUM(int a, int b, int l, int r, int k) { // call l=0, r=M-1, k=0
  int ret = 0;

  if (b < l || r < a) {
    return 0;
  }

  if (a <= l && r <= b) {
    return Data[k] * (r - l + 1) + Datb[k];
  } else {
    ret += Data[k] * (min(b, r) - max(l, a) + 1);
    ret += SUM(a, b, l, (l + r) / 2, k * 2);
    ret += SUM(a, b, (l + r) / 2 + 1, r, 2 * k + 1);
  }
  return ret;
}

int pre_pos[500005];

int last[500005];

int main(void) {

  cin >> N >> Q;
  for (int i = 1; i <= N; i++) {
    cin >> c[i];
  }
  for (int i = 1; i <= Q; i++) {
    cin >> l[i] >> r[i];
  }

  for (int i = 1; i <= N; i++) {
    pre_pos[i] = last[c[i]];
    last[c[i]] = i;
  }

  /*for (int i = 1; i <= N; i++) {
          cout << "pre_pos[" << i << "]= " << pre_pos[i] << endl;
  }*/

  for (int i = 1; i <= Q; i++) {
    V[r[i]].push_back(l[i]);
  }

  for (int i = 1; i <= N; i++) {
    int p = pre_pos[i];
    // cout << "pre_pos[" << i << "]= " << pre_pos[i] << endl;
    ADD(p + 1, i, 0, M - 1, 1, 1);
    for (auto y : V[i]) {
      int num = SUM(y, y, 0, M - 1, 1);
      ans[make_pair(y, i)] = num;
    }
  }

  for (int i = 1; i <= Q; i++) {
    cout << ans[make_pair(l[i], r[i])] << endl;
  }

  /*ADD(0, 3, 0, M - 1, 1, 7);
  ADD(3, 5, 0, M - 1, 1, 9);
  ADD(6, 7, 0, M - 1, 1, 20);

  for (int k = 1; k <= 16; k++) {

          cout << "Data[" << k << "]= " << Data[k] <<"  Datb["<<k<<"]= "<<
  Datb[k] << endl;
  }

  cout << "SUM= " << SUM(6, 7, 0, M - 1, 1) << endl;
  */

  return 0;
}