秋实大哥以周济天下,锄强扶弱为己任,他常对天长叹:安得广厦千万间,大庇天下寒士俱欢颜。
所以今天他又在给一群小朋友发糖吃。
他让所有的小朋友排成一行,从左到右标号。在接下去的时间中,他有时会给一段区间的小朋友每人 v 颗糖,有时会问第 x 个小朋友手里有几颗糖。
这对于没上过学的孩子来说实在太困难了,所以你看不下去了,请你帮助小朋友回答所有的询问。
第一行包含两个整数 n , m ,表示小朋友的个数,以及接下来你要处理的操作数。
接下来的 m 行,每一行表示下面两种操作之一:
0 l r v : 表示秋实大哥给[l,r]这个区间内的小朋友每人v颗糖 1 x : 表示秋实大哥想知道第x个小朋友手里现在有几颗糖
对于每一个 1 x 操作,输出一个整数,表示第 x 个小朋友手里现在的糖果数目。
Sample Input | Sample Output |
---|---|
3 4 0 1 3 1 1 2 0 2 3 3 1 3 |
1 4 |
#include <iostream> #include <cstdio> #include <cstdlib> #include <cstring> #include <string> #include <set> #include <map> #include <queue> #include <algorithm> using namespace std; #define maxn 200005 set<int>jud; long long tr[maxn]; int point[maxn]; //是否可以改掉,只用set而不用再开一个数组? int size = 0; struct operate { int op, l, r, v; operate(int op, int l, int r, int v) { this->op = op; this->l = l; this->r = r; this->v = v; } }; queue<operate>operque; void update(int l, int r, int val) { for (int i = r; i > 0; i -= i&(-i)) tr[i] += val; for (int i = l - 1; i > 0; i -= i&(-i)) tr[i] += (-val); } long long query(int idx) { long long sum = 0; while (idx <= size) { sum += tr[idx]; idx += idx&(-idx); } return sum; } int main() { int l = 0, r = 0, x = 0; int n = 0, m = 0, bl = 0, v = 0; char op[10] = { '\0' }; char fst[10] = { '\0' }; memset(point, 0, sizeof(point)); memset(tr, 0, sizeof(tr)); gets(fst); sscanf(fst,"%d %d", &n, &m); while (m--) { gets(op); if (op[0] == '0') { sscanf(op, "%d %d %d %d", &bl, &l, &r, &v); if (!jud.count(l)) { jud.insert(l); point[++size] = l; } if (!jud.count(r)) { jud.insert(r); point[++size] = r; } operque.push(operate(bl, l, r, v)); } else if (op[0] == '1') { sscanf(op, "%d %d", &bl, &x); if (!jud.count(x)) { jud.insert(x); point[++size] = x; } operque.push(operate(bl, 0, 0, x)); } } sort(point + 1, point + 1 + size); while (!operque.empty()) { operate temp = operque.front(); operque.pop(); if (temp.op & 1) { int pos = lower_bound(point + 1, point + 1 + size, temp.v) - point; printf("%lld\n", query(pos)); } else { int left = lower_bound(point + 1, point + 1 + size, temp.l) - point; int right = lower_bound(point + 1, point + 1 + size, temp.r) - point; update(left, right, temp.v); } } return 0; }