Cod sursa(job #1777380)

Utilizator TincaMateiTinca Matei TincaMatei Data 12 octombrie 2016 13:01:15
Problema Distincte Scor 30
Compilator cpp Status done
Runda Arhiva de probleme Marime 1.53 kb
#include <cstdio>
#include <algorithm>

const int MAX_N = 100000;

int first[1+MAX_N], last[1+MAX_N], next[1+MAX_N], v[1+MAX_N];
struct Query {
  int st, dr, poz;
}query[MAX_N];
long long rezQ[MAX_N];

int aib[1+MAX_N];

inline int lastBit(int x) {
  return x & -x;
}

void updoot(int poz, int x, int n) {
  int i;
  i = poz;
  while(i != 0 && i <= n) {
    aib[i] = aib[i] + x;
    i += lastBit(i);
  }
}

long long query1n(int poz) {
  int i;
  long long rez = 0LL;
  i = poz;
  while(i > 0) {
    rez = rez + aib[i];
    i -= lastBit(i);
  }
  return rez;
}

long long queryInt(int a, int b) {
  return query1n(b) - query1n(a - 1);
}

bool cmp(Query a, Query b) {
  if(a.st < b.st)
    return true;
  return false;
}

int main() {
  int n, q, k, x, j;
  FILE *fin = fopen("distincte.in", "r");
  FILE *fout = fopen("distincte.out", "w");
  fscanf(fin, "%d%d%d", &n, &k, &q);
  for(int i = 1; i <= n; ++i) {
    fscanf(fin, "%d", &x);
    v[i] = x;
    if(first[x] == 0)
      first[x] = last[x] = i;
    else
      last[x] = next[last[x]] = i;
  }
  for(int i = 0; i < q; ++i) {
    fscanf(fin, "%d%d", &query[i].st, &query[i].dr);
    query[i].poz = i;
  }

  std::sort(query, query + q, cmp);

  for(int i = 1; i <= k; ++i) {
    updoot(first[i], i, n);
  }

  j = 0;
  for(int i = 1; i <= n; ++i) {
    while(j < q && i == query[j].st) {
      rezQ[query[j].poz] = queryInt(query[j].st, query[j].dr);
      j++;
    }
    updoot(next[i], v[i], n);
  }

  for(int i = 0; i < q; ++i)
    fprintf(fout, "%lld\n", rezQ[i]);
  fclose(fin);
  fclose(fout);
  return 0;
}