码迷,mamicode.com
首页 > 其他好文 > 详细

poj 3468 整理一下线段树的写法

时间:2017-08-04 21:28:57      阅读:144      评论:0      收藏:0      [点我收藏+]

标签:整理   操作   nod   存在   push   type   iostream   print   scanf   

// 对于延迟更新,我们在updata 和query的时候 pushdown和pushup两个东西都要存在 

#include <iostream> #include <cstdio> #include <cstring> #include <queue> using namespace std; typedef long long ll; struct node { ll l,r,sum,add; } tree[10000*4]; ll a[100001]; //ll x,y; void pushup(int id) { tree[id].sum=tree[id*2].sum+tree[id*2+1].sum; } void build(ll l,ll r,int id) { if(l==r) { tree[id].sum=a[l]; return; } tree[id].l=l; tree[id].r=r; tree[id].add=0; ll mid=(l+r)/2; build(l,mid,id*2); build(mid+1,r,id*2+1); pushup(id); } void pushdown(int id) { if(tree[id].add) { tree[id*2].add +=tree[id].add; tree[id*2+1].add += tree[id].add; tree[id*2].sum += (tree[id*2].r-tree[id*2].l+1)*(tree[id*2].add); tree[id*2+1].sum += (tree[id*2+1].r-tree[id*2+1].l+1)*(tree[id*2+1].add); tree[id].add=0; } } void updata(ll x,ll y,ll l,ll r,int id,ll k) { if(x<=l && r<=y)// 在区间里面 就可以做一定操作 { tree[id].sum += (r-l+1)*k; tree[id].add += k; return; } pushdown(id);// ll mid=(l+r)/2; if(x <= mid) updata(x,y,l,mid,id*2,k); if(y > mid) updata(x,y,mid+1,r,id*2+1,k); pushup(id); } ll query(ll x,ll y,ll l,ll r,int id) { if(x<=l && r<=y) { return tree[id].sum; } pushdown(id); ll mid=(l+r)/2; ll sum=0; if(x<=mid) sum+=query(x,y,l,mid,id*2); if(y>mid) sum+=query(x,y,mid+1,r,id*2+1); pushup(id);// return sum; } int main() { int n,q; ll x,y,k; while(scanf("%d %d",&n,&q)!=EOF) { for(int i=1; i<=n; i++) { scanf("%d",&a[i]); } build(1,n,1); while(q--) { char s[3]; scanf("%s",s); if(s[0]==Q) { scanf("%lld %lld",&x,&y); printf("%lld\n",query(x,y,1,n,1)); } else if(s[0]==C) { scanf("%lld %lld %lld",&x,&y,&k); updata(x,y,1,n,1,k); } } } return 0; }

 

poj 3468 整理一下线段树的写法

标签:整理   操作   nod   存在   push   type   iostream   print   scanf   

原文地址:http://www.cnblogs.com/z1141000271/p/7286911.html

(0)
(0)
   
举报
评论 一句话评论(0
登录后才能评论!
© 2014 mamicode.com 版权所有  联系我们:gaon5@hotmail.com
迷上了代码!