BZOJ 1500 【NOI2005 D1T2】 维修数列 Splay
来源:互联网 发布:max守望先锋数据异常 编辑:程序博客网 时间:2024/05/18 01:53
题目大意:维护一个数列支持以下操作:
这个Splay有毒,抄模板请参照这里
Splay裸题
可啪(?)的题,细节真的很重要
parent指针好像乱七八糟的样子,但是没用上…
在maintain操作前要先pushdown把标记推下去(标记也修改自己,不推标记的话不能保证信息的正确性)
子段和也要用自己的权值去更新
这俩错误查一天…
#include <cstdio>#include <algorithm>#define INF 500000001#define Max(a,b) (a>b?a:b)using namespace std;int n,m,a[500005];struct Node{ Node *ch[2],*pa; int v,s,lmax,rmax,sum,maxs,fix; bool flip,change; Node(int); int cmp(int x){ if(x==ch[0]->s+1) return -1; return x < ch[0]->s+1 ? 0 : 1; } void maintain(); void pushdown();}*null,*root;void Node :: maintain(){ ch[0]->pushdown(); ch[1]->pushdown(); s=ch[0]->s+ch[1]->s+1; sum=ch[0]->sum+ch[1]->sum+v; lmax=Max(ch[0]->lmax,ch[0]->sum+v); lmax=Max(lmax,ch[0]->sum+v+ch[1]->lmax); rmax=Max(ch[1]->rmax,ch[1]->sum+v); rmax=Max(rmax,ch[1]->sum+v+ch[0]->rmax); maxs=Max(ch[0]->maxs,ch[1]->maxs); maxs=Max(maxs,v); maxs=Max(ch[0]->rmax+v,maxs); maxs=Max(ch[1]->lmax+v,maxs); maxs=Max(ch[0]->rmax+v+ch[1]->lmax,maxs); return ;}void Node :: pushdown(){ if(this==null) return ; if(change){ change=false; ch[0]->change=ch[1]->change=true; ch[0]->fix=ch[1]->fix=fix; sum=s*fix; v=fix; if(fix>0)lmax=rmax=maxs=sum; else lmax=rmax=maxs=fix; } if(flip){ flip=false; swap(ch[0],ch[1]); swap(lmax,rmax); ch[0]->flip=!ch[0]->flip; ch[1]->flip=!ch[1]->flip; } return ;}Node :: Node(int v=0):v(v){ pa=ch[0]=ch[1]=null; flip=change=false; if(!null){ lmax=rmax=maxs=-INF; sum=0; s=0; } else maintain();}void init(Node*& o,int l,int r){ int mid=(l+r)>>1; if(l>r){ o=null; return ; } o=new Node(a[mid]); init(o->ch[0],l,mid-1); init(o->ch[1],mid+1,r); if(o->ch[0]!=null) o->ch[0]->pa=o; if(o->ch[1]!=null) o->ch[1]->pa=o; o->maintain(); return ;}void Rotate(Node*& o,int d){ Node* k=o->ch[d^1]; o->ch[d^1]=k->ch[d]; k->ch[d]->pa=o; k->ch[d]=o; k->pa=o->pa; o->pa=k; o->maintain(); k->maintain(); o=k; return ;}void Splay(Node*& o,int k){ o->pushdown(); int d=o->cmp(k); if(d==1) k-=o->ch[0]->s+1; if(d!=-1){ Node* p=o->ch[d]; p->pushdown(); int d2=p->cmp(k); if(d2==1) k-=p->ch[0]->s+1; if(d2!=-1){ Splay(p->ch[d2],k); if(d==d2) Rotate(o,d^1); else Rotate(o->ch[d],d); } Rotate(o,d^1); } return ;}Node* Merge(Node* l,Node* r){ if(l==null) return r; Splay(l,l->s); l->ch[1]=r; r->pa=l; l->maintain(); return l;}void Split(Node* o,int k,Node*& l,Node*& r){ if(!k){ l=null; r=o; return ; } Splay(o,k); l=o; r=o->ch[1]; o->ch[1]=null; l->maintain(); return ;}void Delete(Node*& o){ if(o->ch[0]!=null) Delete(o->ch[0]); if(o->ch[1]!=null) Delete(o->ch[1]); delete o; o=null; return ;}int main(){ freopen("a.in","r",stdin); freopen("a.out","w",stdout); null=new Node(); null->ch[0]=null->ch[1]=null->pa=null; scanf("%d%d",&n,&m); for(int i=1;i<=n;i++) scanf("%d",&a[i]); init(root,1,n); while(m--){ char c[10]; scanf("%s",c); if(c[0]=='I'){//Insert int pos,tot; scanf("%d%d",&pos,&tot); for(int i=1;i<=tot;i++) scanf("%d",&a[i]); Node *o,*l,*r; init(o,1,tot); Split(root,pos,l,r); root=Merge(Merge(l,o),r); } else if(c[0]=='D'){//Delete int pos,tot; scanf("%d%d",&pos,&tot); Node *mid,*l,*r,*o; Split(root,pos-1,l,o); Split(o,tot,mid,r); Delete(mid); root=Merge(l,r); } else if(c[0]=='R'){//Reverse int pos,tot; scanf("%d%d",&pos,&tot); Node *mid,*l,*r,*o; Split(root,pos-1,l,o); Split(o,tot,mid,r); mid->flip=true; root=Merge(Merge(l,mid),r); } else if(c[0]=='G'){//GET-SUM int pos,tot; scanf("%d%d",&pos,&tot); if(!tot){ printf("0\n"); continue; } Node *mid,*l,*r,*o; Split(root,pos-1,l,o); Split(o,tot,mid,r); printf("%d\n",mid->sum); root=Merge(Merge(l,mid),r); } else if(c[2]=='X'){//MAX-SUM printf("%d\n",root->maxs); } else {//MAKE-SAME int pos,tot,cach; scanf("%d%d%d",&pos,&tot,&cach); Node *mid,*l,*r,*o; Split(root,pos-1,l,o); Split(o,tot,mid,r); mid->change=true; mid->fix=cach; root=Merge(Merge(l,mid),r); } } return 0;}
0 0
- BZOJ 1500 【NOI2005 D1T2】 维修数列 Splay
- BZOJ 1500 [NOI2005 D1T2] 维修数列
- BZoj 1500 [NOI2005]维修数列 (Splay 模板)
- BZOJ 1500 NOI2005 维修数列 Splay
- 【BZOJ】1500 [NOI2005]维修数列 【splay】
- 【splay】BZOJ 1500: [NOI2005]维修数列
- bzoj 1500 NOI2005 维修数列 [Splay]
- bzoj 1500: [NOI2005]维修数列(splay)
- [BZOJ 1500][NOI2005]维修数列(Splay)
- BZOJ 1500: [NOI2005]维修数列 Splay
- BZOJ 1500 [NOI2005]维修数列 Splay
- BZOJ 1500: [NOI2005]维修数列 splay
- BZOJ 1500([NOI2005]维修数列-Splay的数列维护)
- 1500: [NOI2005]维修数列(Splay)
- NOI2005 维修数列(splay)
- [NOI2005]维修数列 (Splay)
- [Splay] NOI2005 维修数列
- NOI2005 维修数列 Splay
- Activity之间传值的问题
- 【Python | TensorBoard】用 PCA 可视化 MNIST 手写数字识别数据集
- AJAX交互模型与第一个Ajax案例(JS实现)
- 【 XML 之总结篇】
- 数据结构实验之查找一:二叉排序树
- BZOJ 1500 【NOI2005 D1T2】 维修数列 Splay
- Mod
- node与Express开发学习第一篇
- 深入理解JavaScript运行机制
- SSH之jsp页面
- 第十六周 项目一 - 堆排序
- 使用jax-ws完成第一个webservice的helloword
- Exception sending context initialized event to listener instance of class org.springframework.web.co
- aliyun阿里云Maven仓库地址——加速你的maven构建