记录编号 146982 评测结果 AAAAAAAAAA
题目名称 蝗灾 最终得分 100
用户昵称 GravatarAsm.Def 是否通过 通过
代码语言 C++ 运行时间 3.957 s
提交时间 2015-01-21 22:15:32 内存使用 31.57 MiB
显示代码纯文本
#include <cstdio>
#include <cctype>
#include <cstring>
#include <algorithm>
#include <ctime>
inline void getd(int &x){
	char ch = getchar();
	while(!isdigit(ch))ch = getchar();
	x = ch - '0';
	while(isdigit(ch = getchar()))x = x * 10 - '0' + ch;
}
/********************************************/
using namespace std;
const int maxn = 200003, maxw = 500003;

struct OPT{
	bool NotQ;//1:Add;0:Query
	int val, x, y, T;
	operator int ()const{return x;}
	inline void init(int a, int b, int c, int t){
		x = a, y = b, val = c, T = t;
		NotQ = 1;
	}
	inline void init(int a, int b, int t){
		x = a, y = b, val = 0, T = t;
		NotQ = 0;
	}
}Opt[maxn<<2], *opt[maxn<<2], *Begin[maxn];

struct Fenwick{
	#define lowbit(x) (x & -x)
	int len, A[maxn<<2], ind[maxn<<2], cnt;
	inline void init(int l){len = l;memset(A, 0, sizeof(int) * (len + 1));}
	inline void getind(OPT **L, OPT **R){
		static int tmp[maxn<<2], i;i = 0;cnt = 1;
		while(L < R){tmp[i++] = (*L)->y;++L;}
		sort(tmp, tmp + len);
		ind[cnt] = tmp[0];
		for(i = 1;i < len;++i)
			if(tmp[i] != ind[cnt])ind[++cnt] = tmp[i];
		++cnt;
	}
	inline void Add(int i, int x){
		i = lower_bound(ind + 1, ind + cnt, i) - ind;
		while(i <= len){
			A[i] += x;
			i += lowbit(i);
		}
	}
	inline int Sum(int i){
		i = lower_bound(ind + 1, ind + cnt, i) - ind;
		int ans = 0;
		while(i){
			ans += A[i];
			i ^= lowbit(i);
		}
		return ans;
	}
}F;

int W, N, Qcnt = 0, End;

inline void init(){
	getd(W), getd(N);
	int i, j, t, a, b, c, d;
	for(i = 0,j = 0;i < N;++i){
		getd(t);
		getd(a), getd(b), getd(c);
		if(t == 1){(opt[j] = Opt + j)->init(a, b, c, j);++j;}
		else{
			getd(d);
			Begin[Qcnt++] = Opt + j;
			(opt[j] = Opt + j)->init(a-1, b-1, j);++j;
			(opt[j] = Opt + j)->init(a-1, d, j);++j;
			(opt[j] = Opt + j)->init(c, b-1, j);++j;
			(opt[j] = Opt + j)->init(c, d, j);++j;
		}
	}
	End = j;
}

inline void Solve(int L, int R){
	static OPT *tmp[maxn<<2];
	int len = R - L, mid;
	OPT **it1, **it2;
	if(len == 1)return;
	mid = (L + R) >> 1, it1 = opt + L, it2 = opt + mid;
	if(len == 2){
		if(**it1 > **it2)swap(*it1, *it2);
		else if((*it2)->NotQ==0 && (*it1)->NotQ && (*it1)->y <= (*it2)->y)
			(*it2)->val += (*it1)->val;
		return;
	}
	Solve(L, mid);Solve(mid, R);
	OPT **m = opt + mid, **end = opt + R;
	for(int i = 0;i < len;++i){//merge sort
		if(it1 == m)tmp[i] = *(it2++);
		else if(it2 == end)tmp[i] = *(it1++);
		else if(**it1 > **it2)tmp[i] = *(it2++);
		else tmp[i] = *(it1++);
	}
	it1 = opt + L;
	F.init(len);
	F.getind(tmp, tmp + len);
	for(int i = 0;i < len;++i,++it1){
		*it1 = tmp[i];
		if((*it1)->T < mid && (*it1)->NotQ)
			F.Add((*it1)->y, (*it1)->val);
		else if((*it1)->T >= mid && !(*it1)->NotQ)
			(*it1)->val += F.Sum((*it1)->y);
	}
}

int main(){
	#ifdef DEBUG
	freopen("test", "r", stdin);
	#else
	freopen("locust.in", "r", stdin);
	freopen("locust.out", "w", stdout);
	#endif
	init();
	Solve(0, End);
	int a, b, c, d;
	OPT **it = Begin;
	for(int i = 0;i < Qcnt;++i,++it){
		a = (*it)->val;
		b = (*it+1)->val;
		c = (*it+2)->val;
		d = (*it+3)->val;
		printf("%d\n", a - b - c + d);
	}
	
	return 0;
}