Pagini recente » Cod sursa (job #587131) | Cod sursa (job #1949561) | Cod sursa (job #3191167) | Cod sursa (job #838268) | Cod sursa (job #2816800)
// AIB
// Search in log^2
#include <stdio.h>
#define UPDATE 0
#define SUM_QUERY 1
#define POS_QUERY 2
#define MAX_N 100000
#define LOG_N 16
int n;
int v[MAX_N + 1];
int aib[MAX_N + 1];
inline int leastSignificantBit(int x) {
return x & -x;
}
void build() {
int i;
for (i = 1; i <= n; ++i) {
aib[i] += v[i];
if (i + leastSignificantBit(i) <= n)
aib[i + leastSignificantBit(i)] += aib[i];
}
}
void update(int pos, int val) {
while (pos <= n) {
aib[pos] += val;
pos += leastSignificantBit(pos);
}
}
int query(int pos) {
int result;
result = 0;
while (pos) {
result += aib[pos];
pos -= leastSignificantBit(pos);
}
return result;
}
int value(int pos) {
int result, parent;
result = aib[pos];
parent = pos - leastSignificantBit(pos);
--pos;
while (pos != parent) {
result -= aib[pos];
pos -= leastSignificantBit(pos);
}
return result;
}
inline int query(int left, int right) {
return left == right ? value(left) : query(right) - query(left - 1);
}
int search(int value) {
int pos, step;
pos = 0;
step = 1 << LOG_N;
while (step) {
if (pos + step <= n && query(pos + step) <= value)
pos += step;
step >>= 1;
}
if (pos == 0 || query(pos) != value)
pos = -1;
return pos;
}
int main() {
FILE *fin, *fout;
fin = fopen("aib.in", "r");
fout = fopen("aib.out", "w");
int m, i, type, a, b;
fscanf(fin, "%d%d", &n, &m);
for (i = 1; i <= n; ++i)
fscanf(fin, "%d", &v[i]);
build();
while (m--) {
fscanf(fin, "%d", &type);
if (type == UPDATE) {
fscanf(fin, "%d%d", &a, &b);
update(a, b);
} else if (type == SUM_QUERY) {
fscanf(fin, "%d%d", &a, &b);
fprintf(fout, "%d\n", query(a, b));
} else if (type == POS_QUERY) {
fscanf(fin, "%d", &a);
fprintf(fout, "%d\n", search(a));
}
}
fclose(fin);
fclose(fout);
return 0;
}