比赛 |
cdcqの省选膜你赛 |
评测结果 |
AAAAAAAAAAAAAATTTTTT |
题目名称 |
新史「新幻想史 -现代史-」 |
最终得分 |
70 |
用户昵称 |
Menci |
运行时间 |
15.455 s |
代码语言 |
C++ |
内存使用 |
6.63 MiB |
提交时间 |
2017-04-11 11:52:08 |
显示代码纯文本
#include <cstdio>
// #include <cassert>
#include <algorithm>
const int MAXN = 50000;
const int MAXM = 50000;
enum Type {
Query, Update
};
struct Triple {
Type type;
// x: The index in operate sequence
// y: The input 'time'
int x, y, l, r;
// For update
int delta;
bool applied;
// For query
long long *ans;
Triple() {}
Triple(int x, int y, int l, int r, int delta) : type(Update), x(x), y(y), l(l), r(r), delta(delta), applied(false), ans(NULL) {}
Triple(int x, int y, int l, int r, long long *ans) : type(Query), x(x), y(y), l(l), r(r), delta(0), applied(false), ans(ans) {}
bool operator<(const Triple &other) const {
return x < other.x;
}
void print() {
if (type == Update) printf("Update(%d, %d, [%d, %d], %d)\n", x, y, l, r, delta);
else printf("Query(%d, %d, [%d, %d])\n", x, y, l, r);
}
} a[MAXN + MAXM + 1];
struct SegT {
int l, r, mid;
SegT *lc, *rc;
long long sum, tag;
SegT(int pos) : l(pos), r(pos), mid(pos), lc(NULL), rc(NULL), sum(0), tag(0) {}
SegT(int l, int r, SegT *lc, SegT *rc) : l(l), r(r), mid(l + (r - l) / 2), lc(lc), rc(rc), sum(0), tag(0) {}
void maintain() {
sum = lc->sum + rc->sum;
}
void pushDown() {
if (tag) {
lc->cover(tag);
rc->cover(tag);
tag = 0;
}
}
void cover(long long delta) {
sum += delta * (r - l + 1);
tag += delta;
}
void update(int l, int r, long long delta) {
if (l > this->r || r < this->l) return;
else if (l <= this->l && r >= this->r) cover(delta);
else pushDown(), lc->update(l, r, delta), rc->update(l, r, delta), maintain();
}
long long query(int l, int r) {
if (l > this->r || r < this->l) return 0;
else if (l <= this->l && r >= this->r) return sum;
else return pushDown(), lc->query(l, r) + rc->query(l, r);
}
static SegT *build(int l, int r) {
if (l == r) return new SegT(l);
else {
int mid = l + (r - l) / 2;
return new SegT(l, r, build(l, mid), build(mid + 1, r));
}
}
} *seg;
inline void cdq(Triple *l, Triple *r) {
/*
puts("");
for (Triple *p = l; p <= r; p++) p->print();
*/
if (l == r) return;
Triple *mid = l + (r - l) / 2;
cdq(l, mid);
cdq(mid + 1, r);
static Triple tmp[MAXN + MAXM + 1];
for (Triple *p1 = l, *p2 = mid + 1, *p = tmp; p <= tmp + (r - l); p++) {
if (p1 <= mid && (p2 > r || p1->y <= p2->y)) {
*p = *p1++;
if (p->type == Update) {
seg->update(p->l, p->r, p->delta);
p->applied = true;
// printf("seg->update([%d, %d], %d)\n", p->l, p->r, p->delta);
}
} else {
*p = *p2++;
if (p->type == Query) *p->ans += seg->query(p->l, p->r);
}
}
for (Triple *p = l, *q = tmp; p <= r; p++, q++) {
*p = *q;
if (p->applied) {
p->applied = false;
seg->update(p->l, p->r, -p->delta);
// printf("seg->update([%d, %d], %d)\n", p->l, p->r, -p->delta);
}
}
// for (int i = 1; i <= 5; i++) assert(seg->query(i, i) == 0);
}
int main() {
freopen("cdcq_a.in", "r", stdin);
freopen("cdcq_a.out", "w", stdout);
int n, m;
scanf("%d %d", &n, &m);
seg = SegT::build(1, n);
int cnt = 0;
for (int i = 1; i <= n; i++) {
int x;
scanf("%d", &x);
++cnt;
a[cnt] = Triple(cnt, 0, i, i, x);
}
static long long ans[MAXM + 1];
int qCnt = 0;
for (int i = 1; i <= m; i++) {
char s[2];
scanf("%s", s);
if (*s == 'Q') {
int l, r, time;
scanf("%d %d %d", &l, &r, &time);
++qCnt;
++cnt;
a[cnt] = Triple(cnt, time, l, r, &ans[qCnt]);
} else {
int l1, r1, delta1, l2, r2, delta2, time;
scanf("%d %d %d %d %d %d %d", &l1, &r1, &delta1, &l2, &r2, &delta2, &time);
++cnt;
a[cnt] = Triple(cnt, time, l1, r1, -delta1);
++cnt;
a[cnt] = Triple(cnt, time, l2, r2, delta2);
}
}
std::sort(a + 1, a + cnt + 1);
cdq(a + 1, a + cnt);
for (int i = 1; i <= qCnt; i++) printf("%lld\n", ans[i]);
}