Another Array of Orz Pandas

Another Array of Orz Pandas

题目链接:http://acm.xidian.edu.cn/problem.php?id=1187

线段树

线段树维护区间和以及区间内各个数平方和,对于每一个询问ans=(sum2-pow_sum)/2

代码如下:

 1 #include<cstdio>
 2 #include<cstring>
 3 #define lson (x<<1)
 4 #define rson (x<<1|1)
 5 #define mid ((l+r)>>1)
 6 #define N 100007
 7 typedef long long LL;
 8 struct nod{
 9     LL sum,lazy,or2zds;
10 }a[N<<2];
11 const LL mod=1e9+7;
12 const LL Max=1e9;
13 LL n,m;
14 void push_up(LL x){
15     a[x].sum=(a[lson].sum+a[rson].sum)%mod;
16     a[x].or2zds=(a[lson].or2zds+a[rson].or2zds)%mod;
17 }
18 void push_down(LL x,LL l,LL r){
19     a[lson].or2zds=(a[lson].or2zds+(a[x].lazy*a[x].lazy)%mod*(mid+1-l)+2*a[x].lazy*a[lson].sum+mod)%mod;
20     a[lson].sum=(a[lson].sum+a[x].lazy*(mid+1-l))%mod;
21     a[lson].lazy=(a[lson].lazy+a[x].lazy)%mod;
22     a[rson].or2zds=(a[rson].or2zds+(a[x].lazy*a[x].lazy)%mod*(r-mid)+2*a[x].lazy*a[rson].sum+mod)%mod;
23     a[rson].sum=(a[rson].sum+a[x].lazy*(r-mid))%mod;
24     a[rson].lazy=(a[rson].lazy+a[x].lazy)%mod;
25     a[x].lazy=0;
26 }
27 void add(LL x,LL l,LL r,LL cl,LL cr,LL v){
28     if(cl<=l&&r<=cr){
29         a[x].or2zds=(a[x].or2zds+(v*v)%mod*(r-l+1)%mod+2*v*a[x].sum)%mod;
30         a[x].sum=(a[x].sum+v*(r-l+1))%mod;
31         a[x].lazy=(a[x].lazy+v)%mod;
32         return;
33     }
34     if(a[x].lazy!=0)push_down(x,l,r);
35     if(cl<=mid)add(lson,l,mid,cl,cr,v);
36     if(mid<cr)add(rson,mid+1,r,cl,cr,v);
37     push_up(x);
38 }
39 void query(LL x,LL l,LL r,LL ql,LL qr,LL &sum,LL &sum2){
40     if(ql<=l&&r<=qr){
41         sum=(sum+a[x].sum)%mod;
42         sum2=(sum2+a[x].or2zds)%mod;
43         return;
44     }
45     if(a[x].lazy!=0)push_down(x,l,r);
46     if(ql<=mid)query(lson,l,mid,ql,qr,sum,sum2);
47     if(mid<qr)query(rson,mid+1,r,ql,qr,sum,sum2);
48 }
49 int main(void){
50     while(~scanf("%lld%lld",&n,&m)){
51         memset(a,0,sizeof(a));
52         LL l,r,op,k;
53         for(LL i=0;i<m;i++){
54             scanf("%lld",&op);
55             if(op==1){
56                 scanf("%lld%lld%lld",&l,&r,&k);
57                 add(1,1,n,l,r,k);
58             }else {
59                 scanf("%lld%lld",&l,&r);
60                 LL sum=0,sum2=0;
61                 query(1,1,n,l,r,sum,sum2);
62                 printf("%lld\n",(sum*sum%mod-sum2+mod)%mod*500000004%mod);
63             }
64         }
65     }
66     return 0;
67 }

 

posted @ 2016-12-05 15:33  barriery  阅读(275)  评论(0编辑  收藏  举报