思路:线段树单点修改+区间查询。
#include<cstdio> #include<cstring> #include<iostream> #include<algorithm> #define MAXN 50001 using namespace std; string s; int t,n,tot; struct nond{ int l,r,sum; }tree[MAXN*4]; void up(int now){ tree[now].sum=tree[now*2].sum+tree[now*2+1].sum; } void build(int now,int l,int r){ tree[now].l=l;tree[now].r=r; if(tree[now].l==tree[now].r){ scanf("%d",&tree[now].sum); return ; } int mid=(tree[now].l+tree[now].r)/2; build(now*2,l,mid); build(now*2+1,mid+1,r); up(now); } void change(int now,int x,int k){ if(tree[now].l==tree[now].r){ tree[now].sum+=k; return ; } int mid=(tree[now].l+tree[now].r)/2; if(x<=mid) change(now*2,x,k); else change(now*2+1,x,k); up(now); } int query(int now,int l,int r){ if(tree[now].l==l&&tree[now].r==r) return tree[now].sum; int mid=(tree[now].l+tree[now].r)/2; if(r<=mid) return query(now*2,l,r); else if(l>mid) return query(now*2+1,l,r); else return query(now*2,l,mid)+query(now*2+1,mid+1,r); } int main(){ scanf("%d",&t); while(t--){ tot++;printf("Case %d:\n",tot); scanf("%d",&n); build(1,1,n); int x,y; while(cin>>s&&s[0]!=‘E‘){ if(s[0]==‘Q‘){ scanf("%d%d",&x,&y);printf("%d\n",query(1,x,y)); } else if(s[0]==‘A‘){ scanf("%d%d",&x,&y);change(1,x,y); } else if(s[0]==‘S‘){ scanf("%d%d",&x,&y);change(1,x,-y); } } } }