博客
关于我
强烈建议你试试无所不能的chatGPT,快点击我
suoi37 清点更多船只 (卡空间线段树)
阅读量:4978 次
发布时间:2019-06-12

本文共 2861 字,大约阅读时间需要 9 分钟。

sbw巨佬的卡空间方法,把线段树的叶节点只记到长度为16的区间,然后在叶节点上暴力修改查询,这样点数是$\frac{N}{8}$的,可以过...

orz

1 #include
2 #define pa pair
3 #define CLR(a,x) memset(a,x,sizeof(a)) 4 using namespace std; 5 typedef long long ll; 6 const int maxn=(1<<20),maxp=(1<<18)+10; 7 8 inline ll rd(){ 9 ll x=0;char c=getchar();int neg=1; 10 while(c<'0'||c>'9'){
if(c=='-') neg=-1;c=getchar();} 11 while(c>='0'&&c<='9') x=x*10+c-'0',c=getchar(); 12 return x*neg; 13 } 14 15 ll sum[maxp],v[maxn],laz[maxp]; 16 int N,M; 17 18 inline void update(int p,int l,int r){ 19 if(r-l+1<=16){ 20 sum[p]=0; 21 for(int i=l;i<=r;i++){ 22 sum[p]+=v[i]; 23 } 24 }else{ 25 sum[p]=sum[p<<1]+sum[p<<1|1]; 26 } 27 } 28 inline void deal(int p,int l,int r,ll z){ 29 if(r-l+1<=16){ 30 for(int i=l;i<=r;i++){ 31 v[i]+=z,sum[p]+=z; 32 } 33 }else sum[p]+=z*(r-l+1); 34 } 35 36 inline void pushdown(int p,int l,int r){ 37 if(!laz[p]||r-l+1<=16) return; 38 int a=p<<1,b=p<<1|1,m=l+r>>1; 39 deal(a,l,m,laz[p]),deal(b,m+1,r,laz[p]); 40 laz[a]+=laz[p],laz[b]+=laz[p]; 41 laz[p]=0; 42 } 43 44 void build(int p,int l,int r){ 45 if(r-l+1<=16) update(p,l,r); 46 else{ 47 int m=l+r>>1; 48 build(p<<1,l,m); 49 build(p<<1|1,m+1,r); 50 // printf("!%d %d %d\n",p,l,r); 51 update(p,l,r); 52 } 53 } 54 55 ll query(int p,int l,int r,int x,int y){ 56 // printf("~~%d %d %d %d %d\n",p,l,r,x,y); 57 pushdown(p,l,r); 58 if(x<=l&&r<=y) return sum[p]; 59 if(r-l+1<=16){ 60 ll re=0; 61 for(int i=x;i<=y;i++) re+=v[i]; 62 return re; 63 } 64 int m=l+r>>1;ll re=0; 65 if(x<=m) re=query(p<<1,l,m,x,min(m,y)); 66 if(y>=m+1) re+=query(p<<1|1,m+1,r,max(x,m+1),y); 67 return re; 68 } 69 70 void add(int p,int l,int r,int x,int y,ll z){ 71 // printf("!!%d %d %d %d %d\n",p,l,r,x,y); 72 pushdown(p,l,r); 73 if(r-l+1<=16){ 74 for(int i=x;i<=y;i++) 75 v[i]+=z,sum[p]+=z; 76 }else if(x<=l&&r<=y){ 77 deal(p,l,r,z); 78 laz[p]+=z; 79 }else{ 80 int m=l+r>>1; 81 if(x<=m) add(p<<1,l,m,x,min(m,y),z); 82 if(y>=m+1) add(p<<1|1,m+1,r,max(m+1,x),y,z); 83 update(p,l,r); 84 } 85 } 86 87 int main(){ 88 //freopen("","r",stdin); 89 int i; 90 N=rd(),M=rd(); 91 for(i=1;i<=N;i++) 92 v[i]=rd(); 93 N=1<<((int)log2(N)+1); 94 build(1,1,N); 95 for(i=1;i<=M;i++){ 96 char s[10]; 97 scanf("%s",s); 98 int l=rd(),r=rd(); 99 if(s[1]=='d'){100 int d=rd();101 add(1,1,N,l,r,d);102 }else printf("%lld\n",query(1,1,N,l,r));103 }104 return 0;105 }

 

转载于:https://www.cnblogs.com/Ressed/p/9794670.html

你可能感兴趣的文章
React中的表单元素
查看>>
软件工程(2018)第一次作业
查看>>
三 HTML框架标签
查看>>
javaweb学习总结二十四(servlet经常用到的对象)
查看>>
作用域(Scope)
查看>>
VCL组件之TStrings
查看>>
iOS之隐藏状态栏
查看>>
0728 会议记录
查看>>
验证码
查看>>
config.sys文件如何配置(基础知识)
查看>>
CentOS下安装MySQL
查看>>
android SimpleAdapter类使用方法
查看>>
再谈每周工作不要超过 40 小时
查看>>
vue 事件中的 .native
查看>>
CSS3 多列
查看>>
Verilog HDL中的运算符关系
查看>>
常用短语
查看>>
经典wordpress插件(wp插件)集合
查看>>
测试2
查看>>
Eclipse Workspace编码与网页乱码
查看>>