gate
来清理下以前收藏的水题吧...
这道题是NOIP2018之前学长们押的题之一,虽然当时不会写,但是做法现在还记得
将一个数组上加一个等差数列,两次差分即可。
等差数列首项为s,末项为e,那么就有
l l+1 l+2 l+3 ... r r+1 r+2 a[i] s s+d s+2d s+3d ... e 0 0 b[i] s d d d ... d -e 0 c[i] s d-s 0 0 ... 0 -e-d e
因此,需要改动的就只有l, l+1, r+1, r+2这四项
代码如下
const int maxn = 1e7+10;
int n,m,l,r;
long long s,e,d,sum,ans;
long long a[maxn],b[maxn];
int main() {
scanf("%d%d",&n,&m);
for(int i = 1; i <= m; i++) {
scanf("%d%d%lld%lld",&l,&r,&s,&e);
d = (e-s)/(r-l);
b[l] += s;
b[l+1] += d-s;
b[r+1] += -e-d;
b[r+2] += e;
}
for(int i = 1; i <= n; i++) {
b[i] += b[i-1];
a[i] += a[i-1] + b[i];
sum ^= a[i];
ans = max(ans,a[i]);
}
printf("%lld %lld",sum,ans);
return 0;
}