洛谷P2042 [NOI2005]维护数列
#include<cstdio>
#include<cstdlib>
#include<algorithm>
#include<cstring>
#include<stack>
#define Tp Treap*
#define DTp pair<Tp,Tp>
#define ft first
#define sc second
#define INF 0x7f7f7f7f
#define MAXN 500000+10
using namespace std;
int n,m;
int a[MAXN];
struct Treap{
Tp l;Tp r;
int key,fix;
int size,sum,lx,rx,mx,tag;
};
Tp root;
stack<Tp> s;
Tp new_node(int v){
Tp ret;
if(s.empty())ret=new Treap;
else ret=s.top(),s.pop();
ret->l=ret->r=NULL;
ret->key=ret->sum=v;
ret->lx=ret->rx=ret->mx=v;
ret->tag=-INF;
ret->size=,ret->fix=rand();
return ret;
}
int Size(Tp A){return (A?A->size:);}
int Sum(Tp A){return (A?A->sum:);}
int Lx(Tp A){return (A?A->lx:-INF);}
int Rx(Tp A){return (A?A->rx:-INF);}
int Mx(Tp A){return (A?A->mx:-INF);}
void upd(Tp A){
A->size=Size(A->l)+Size(A->r)+;
A->sum=Sum(A->l)+Sum(A->r)+A->key;
A->mx=max(max(Mx(A->l),Mx(A->r)),A->key+max(Rx(A->l),)+max(Lx(A->r),));
A->lx=max(Lx(A->l),Sum(A->l)+A->key+max(Lx(A->r),));
A->rx=max(Rx(A->r),Sum(A->r)+A->key+max(Rx(A->l),));
}
void Print(Tp A){
if(!A)return;
// pushdown(A);
// printf("key=%d,size=%d,sum=%d,lx=%d,rx=%d,mx=%d\n",A->key,A->size,A->sum,A->lx,A->rx,A->mx);
Print(A->l);
printf("%d ",A->key);
Print(A->r);
if(A==root)printf("\n");
}
void update(Tp A,int x){
if(!A||-INF==x)return;
if(x!=INF){
A->tag=x;
A->key=x;
A->sum=x*A->size;
A->mx=A->lx=A->rx=(x>?A->sum:x);
}
else{
if(A->tag!=INF&&A->tag!=-INF)return;
swap(A->l,A->r);
swap(A->lx,A->rx);
A->tag=-A->tag;
}
}
void pushdown(Tp A){
update(A->l,A->tag);
update(A->r,A->tag);
A->tag=-INF;
}
Tp build(int L,int R){
if(L>R)return NULL;
int mid=(L+R)>>;
Tp ret=new_node(a[mid]);
ret->l=build(L,mid-);
ret->r=build(mid+,R);
upd(ret);
return ret;
}
Tp Merge(Tp A,Tp B){
if(!A)return B;
if(!B)return A;
if(A->fix<B->fix){
pushdown(A);
A->r=Merge(A->r,B);
upd(A);
return A;
}
else{
pushdown(B);
B->l=Merge(A,B->l);
upd(B);
return B;
}
}
DTp Split(Tp A,int k){
if(!A)return DTp(NULL,NULL);
pushdown(A);
DTp y;
if(Size(A->l)>=k){
y=Split(A->l,k);
A->l=y.sc;
upd(A);
y.sc=A;
}
else{
y=Split(A->r,k-Size(A->l)-);
A->r=y.ft;
upd(A);
y.ft=A;
}
return y;
}
int pos,len;
void Insert(){
scanf("%d%d",&pos,&len);
for(int i=;i<=len;i++)scanf("%d",&a[i]);
DTp x=Split(root,pos);
root=Merge(x.ft,Merge(build(,len),x.sc));
}
void Del(Tp A){
if(!A)return;
s.push(A);
Del(A->l);
Del(A->r);
}
void Delete(){
scanf("%d%d",&pos,&len);
DTp x=Split(root,pos-);
DTp y=Split(x.sc,len);
Del(y.ft);
root=Merge(x.ft,y.sc);
}
void MakeSame(){
int v;
scanf("%d%d%d",&pos,&len,&v);
DTp x=Split(root,pos-);
DTp y=Split(x.sc,len);
update(y.ft,v);
root=Merge(x.ft,Merge(y.ft,y.sc));
}
void Rev(){
scanf("%d%d",&pos,&len);
DTp x=Split(root,pos-);
DTp y=Split(x.sc,len);
update(y.ft,INF);
root=Merge(x.ft,Merge(y.ft,y.sc));
}
int GetSum(){
scanf("%d%d",&pos,&len);
if(!len)return ;
DTp x=Split(root,pos-);
DTp y=Split(x.sc,len);
int ans=y.ft->sum;
root=Merge(x.ft,Merge(y.ft,y.sc));
return ans;
}
int MaxSum(){
return root->mx;
}
void init(){
scanf("%d%d",&n,&m);
for(int i=;i<=n;i++)scanf("%d",&a[i]);
root=build(,n);
}
void solve(){
char s[];
while(m--){
scanf("%s",s);
if('I'==s[])Insert();
else if('D'==s[])Delete();
else if('M'==s[]&&'E'==s[])MakeSame();
else if('R'==s[])Rev();
else if('G'==s[])printf("%d\n",GetSum());
else printf("%d\n",MaxSum());
}
}
int main()
{
// freopen("testdata.in.txt","r",stdin);
// freopen("my.out","w",stdout);
init();
solve();
return ;
}
洛谷P2042 [NOI2005]维护数列的更多相关文章
- 洛谷 P2042 [NOI2005]维护数列-Splay(插入 删除 修改 翻转 求和 最大的子序列)
因为要讲座,随便写一下,等讲完有时间好好写一篇splay的博客. 先直接上题目然后贴代码,具体讲解都写代码里了. 参考的博客等的链接都贴代码里了,有空再好好写. P2042 [NOI2005]维护数列 ...
- 洛谷.2042.[NOI2005]维护数列(Splay)
题目链接 2017.12.24 第一次写: 时间: 2316ms (1268ms) 空间: 19.42MB (19.5MB)(O2) 注:洛谷测的时间浮动比较大 /* 插入一段数:将这些数先单独建一棵 ...
- 【洛谷P2042】维护数列
题目大意:维护一个序列,支持区间插入,区间删除,区间翻转,查询区间元素和,查询区间最大子段和操作. 题解:毒瘤题...QAQ打完这道题发现自己以前学了一个假的 Splay.. 对于区间操作,用 spl ...
- P2042 [NOI2005]维护数列 && Splay区间操作(四)
到这里 \(A\) 了这题, \(Splay\) 就能算入好门了吧. 今天是个特殊的日子, \(NOI\) 出成绩, 大佬 \(Cu\) 不敢相信这一切这么快, 一下子机房就只剩我和 \(zrs\) ...
- P2042 [NOI2005]维护数列[splay或非旋treap·毒瘤题]
P2042 [NOI2005]维护数列 数列区间和,最大子列和(必须不为空),支持翻转.修改值.插入删除. 练码力的题,很毒瘤.个人因为太菜了,对splay极其生疏,犯了大量错误,在此记录,望以后一定 ...
- Luogu P2042 [NOI2005]维护数列(平衡树)
P2042 [NOI2005]维护数列 题意 题目描述 请写一个程序,要求维护一个数列,支持以下\(6\)种操作:(请注意,格式栏中的下划线'_'表示实际输入文件中的空格) 输入输出格式 输入格式: ...
- BZOJ 1500 Luogu P2042 [NOI2005] 维护数列 (Splay)
手动博客搬家: 本文发表于20180825 00:34:49, 原地址https://blog.csdn.net/suncongbo/article/details/82027387 题目链接: (l ...
- Luogu P2042 [NOI2005]维护数列
题目描述 请写一个程序,要求维护一个数列,支持以下 6 种操作:(请注意,格式栏 中的下划线' _ '表示实际输入文件中的空格) 输入输出格式 输入格式: 输入文件的第 1 行包含两个数 N 和 M, ...
- P2042 [NOI2005]维护数列
思路 超级恶心的pushdown 昏天黑地的调 让我想起了我那前几个月的线段树2 错误 这恶心的一道题终于过了 太多错误,简直说不过来 pushup pushdown 主要就是这俩不太清晰,乱push ...
随机推荐
- 关于python中的operator.itemgetter()函数的用法
1. operator.itemgetter(num)函数 表示对对象的第num维数据进行操作获取. >>>import operator >>>a = [1, 2 ...
- 学号:201621123032 《Java程序设计》第11周学习总结
1:本周学习总结 1.1.:以你喜欢的方式(思维导图或其他)归纳总结多线程相关内容. 2:书面作业 2.1.: 源代码阅读:多线程程序BounceThread 1.1: BallRunnable类有什 ...
- python的测试
测试 知识点 单元测试概念 使用 unittest 模块 测试用例的编写 异常测试 测试覆盖率概念 使用 coverage 模块 实验步骤 1. 应该测试什么? 如果可能的话,代码库中的所有代码都要测 ...
- MySQL 服务安装及命令使用
MySQL 服务安装及命令使用 课程来源说明 本节实验后续至第17节实验为本课程的进阶篇,都基于 MySQL 官方参考手册制作,并根据实验楼环境进行测试调整改编.在此感谢 MySQL 的开发者,官方文 ...
- 面试必问---HashMap原理分析
一.HashMap的原理 众所周知,HashMap是用来存储Key-Value键值对的一种集合,这个键值对也叫做Entry,而每个Entry都是存储在数组当中,因此这个数组就是HashMap的主干.H ...
- C语言使用vs2013进行编辑
由于vs2013是微软开发的产品所以在windows平台下无限兼容windows所有虽然比较大,但是还是比较值得 但是在运行C程序的遇到问题就是控制台一闪而过通过ctrl+F5执行也是不管用: #in ...
- MSIL实用指南-生成接口
本篇讲解怎么样生成接口,即interface. 一.创建类型创建一个接口类型依旧用ModuleBuilder的DefineType方法,但是它的第二个参数必须要有TypeAttributes.Inte ...
- SQL Server 实现类似C#中 PadLeft功能
USE [Test] GO SET ANSI_NULLS ON GO SET QUOTED_IDENTIFIER ON GO --@column 表示字段或者常量,@paddingChar 表示 补位 ...
- kubernetes入门(02)kubernetes的架构
一.kubernetes的主从架构 kubectl,全称 Kubernetes Control Plane,它表示Kubernetes为了实现最终的目标而构建的一组集群范围内的进程,这组进程相互协调, ...
- 页面加载loading动画
关于页面加载的loading动画,能度娘到的大部分都是通过定时器+蒙层实现的,虽然表面上实现了动画效果,实际上动化进程和页面加载进程是没有什么关系的,只是设置几秒钟之后关闭蒙层,但假如页面须要加载的元 ...