线段树模板题

 1 #include<cstdio>
 2 #include<cstring>
 3 using namespace std;
 4 const int N=50010;
 5 int t,n,h[N],sum[4*N];
 6 char ch[20];
 7 void update(int),build(int,int,int),
 8   modify(int,int,int,int,int),work();
 9 int query(int,int,int,int,int),turn();
10 int main(){
11     scanf("%d",&t);
12     for (int k=1;k<=t;k++){
13         memset(sum,0,sizeof(sum));
14         printf("Case %d:\n",k);
15         work();
16     }
17     return 0;
18 }
19 int turn(){
20     if (ch[0]=='Q') return 1;
21     if (ch[0]=='E') return 0;
22     if (ch[0]=='A') return 2;
23     return 3;
24 }
25 void work(){
26     int a,b,c;
27     scanf("%d",&n);
28     for (int i=1;i<=n;i++)
29         scanf("%d",&h[i]);
30     build(1,1,n);
31     getchar();scanf("%s",ch);
32     c=turn();
33     while (c){
34         scanf("%d %d",&a,&b);
35         if (c==1)
36             printf("%d\n",query(1,1,n,a,b));
37         else{
38             if (c==3) b*=-1;
39             modify(1,1,n,a,b);
40         }
41         getchar();scanf("%s",ch);
42         c=turn();
43     }
44 }
45 void update(int i){
46     sum[i]=sum[i<<1]+sum[i<<1|1];
47 }
48 void build(int i,int l,int r){
49     if (l==r){
50         sum[i]=h[l];return;
51     }
52     int mid=(l+r)>>1;
53     build(i<<1,l,mid);
54     build(i<<1|1,mid+1,r);
55     update(i);
56 }
57 int query(int i,int l,int r,int L,int R){
58     if (L<=l&&r<=R) return sum[i];
59     int mid=(l+r)>>1,ans=0;
60     if (L<=mid) ans+=query(i<<1,l,mid,L,R);
61     if (R>mid) ans+=query(i<<1|1,mid+1,r,L,R);
62     return ans;
63 }
64 void modify(int i,int l,int r,int x,int d){
65     if (l==r){
66         sum[i]+=d;return;
67     }
68     int mid=(l+r)>>1;
69     if (x<=mid) modify(i<<1,l,mid,x,d);
70     else modify(i<<1|1,mid+1,r,x,d);
71     update(i);
72 }
STD

 

posted on 2016-09-17 19:44  Absolutezero  阅读(381)  评论(0)    收藏  举报