luogu P4231 三步必杀 差分数组+差分数组
P4231 三步必杀 差分数组+差分数组
一看等差数列思路就往奇怪的地方去了……
突然想到常数列前缀和就是等差
又想到上周D1T1后缀和的后缀和就是类似的东西
所以在题目明显暗示差分的情况下做一下差分的差分
然后由于最后求前缀和只需要1~n所以就只需要每次在差分数组上修改就可以了
也只需要这一个数组
然后n<=1e7……彻底维护不了前缀和了 (本来还想用树状数组的……)
区间异或和最大值都扫一遍就行
证明具体描述不清楚 拿差分推一遍两遍就行
Code:
1 #include<cstdio> 2 #include<algorithm> 3 #include<cstring> 4 #include<cmath> 5 #define rep(i,a,n) for(int i = a;i <= n;i++) 6 #define per(i,n,a) for(int i = n;i >= a;i--) 7 #define ms(a,b) memset(a,b,sizeof a) 8 #define inf 2147483647 9 using namespace std; 10 typedef long long ll; 11 ll read() { 12 ll as = 0,fu = 1; 13 char c = getchar(); 14 while(c < '0' || c > '9') { 15 if(c == '-') fu = -1; 16 c = getchar(); 17 } 18 while(c >= '0' && c <= '9') { 19 as = as * 10 + c - '0'; 20 c = getchar(); 21 } 22 return as * fu; 23 } 24 const int N = 10000005; 25 //head 26 ll n,m; 27 ll ccf[N]; 28 ll cf,ori; 29 ll maxx,XOR; 30 int main() { 31 n = read(); 32 m = read(); 33 rep(i,1,m) { 34 int l = read(); 35 int r = read(); 36 ll s = read(); 37 ll e = read(); 38 ll d = (e-s) / (r-l); 39 //gong_cha 40 ccf[l] += s; 41 ccf[l+1] += d-s; 42 ccf[r+1] += (-d-e); 43 ccf[r+2] += e; 44 } 45 rep(i,1,n) { 46 cf += ccf[i]; 47 ori += cf; 48 maxx = max(maxx,ori); 49 XOR ^= ori; 50 } 51 printf("%lld %lld\n",XOR,maxx); 52 return 0; 53 }
> 别忘了 总有人在等着你