洛谷 P2042 维护数列
来源:互联网 发布:gcf软件下载 编辑:程序博客网 时间:2024/06/15 18:53
这题…mdzz。我想打人。
【分析】
六种操作都比较基本…然而拼到一起就很难了呢呵呵。(对我来说很难)
大家直接参考代码吧。注意一点就是要把删除节点的编号存起来,insert的时候用这些节点,要不然会RE RE RE RE RE RE RE RE RE RERE
【代码】
#include<iostream>#include<cstring>#include<cstdio>#define ll long long#define inf 0x3f3f3f3f#define M(a) memset(a,-inf,sizeof a)#define fo(i,j,k) for(i=j;i<=k;i++)using namespace std;const int mxn=500000;int n,m,sz,opt,root,top;int a[mxn],c[mxn],f[mxn],ch[mxn][2],key[mxn],size[mxn],tag[mxn],rub[mxn];int reverse[mxn],sum[mxn],lmx[mxn],rmx[mxn],mx[mxn];inline int get(int x){ if(ch[f[x]][1]==x) return 1;return 0;}inline void update(int now){ if(!now) return; size[now]=1; int l=ch[now][0],r=ch[now][1]; if(l) size[now]+=size[l]; if(r) size[now]+=size[r]; lmx[now]=max(lmx[l],sum[l]+key[now]+max(0,lmx[r])); rmx[now]=max(rmx[r],sum[r]+key[now]+max(0,rmx[l])); mx[now]=max(max(mx[l],mx[r]),max(0,rmx[l])+max(0,lmx[r])+key[now]); sum[now]=sum[l]+sum[r]+key[now];}inline void rev(int x) { if (!x) return; swap(lmx[x],rmx[x]); swap(ch[x][0],ch[x][1]); reverse[x]^=1; } inline void replace(int x,int d) { if (!x) return; key[x]=d,sum[x]=d*size[x]; lmx[x]=rmx[x]=mx[x]=max(d,d*size[x]); tag[x]=1; } inline void pushdown(int x) { if(reverse[x]) { if(ch[x][0]) rev(ch[x][0]); if(ch[x][1]) rev(ch[x][1]); reverse[x]=0; } if (tag[x]) { if(ch[x][0]) replace(ch[x][0],key[x]); if(ch[x][1]) replace(ch[x][1],key[x]); tag[x]=0; } } inline void rotate(int x){ pushdown(x); int fa=f[x],fafa=f[fa],which=get(x); ch[fa][which]=ch[x][which^1],f[ch[fa][which]]=fa; ch[x][which^1]=fa,f[fa]=x; f[x]=fafa; if(fafa) ch[fafa][ch[fafa][1]==fa]=x; update(fa),update(x);}inline void splay(int x,int lastfa){ for(int fa;(fa=f[x])!=lastfa;rotate(x)) if(f[fa]!=lastfa) rotate(get(x)==get(fa)?fa:x); if(!lastfa) root=x;}inline int build(int fa,int l,int r){ if(l>r) return 0; int now,mid=l+r>>1;; if(!top) now=++sz; else now=rub[top--]; sum[now]=lmx[now]=rmx[now]=mx[now]=key[now]=a[mid],f[now]=fa,size[now]=1; tag[now]=reverse[now]=0; ch[now][0]=build(now,l,mid-1); ch[now][1]=build(now,mid+1,r); update(now); return now;}inline int number(int x){ int now=root; while(1) { pushdown(now); if(ch[now][0] && x<=size[ch[now][0]]) now=ch[now][0]; else { if(x==size[ch[now][0]]+1) return now; x=x-size[ch[now][0]]-1; now=ch[now][1];pushdown(now); } }}inline void del(int x){ if(!x) return; rub[++top]=x; if(ch[x][0]) del(ch[x][0]); if(ch[x][1]) del(ch[x][1]);}int main(){// freopen("rand.txt","r",stdin);// freopen("mine.txt","w",stdout); M(lmx),M(rmx),M(mx); char str[105]; int i,j,k,x,y,z,w,tot,posi; scanf("%d%d",&n,&m); fo(i,2,n+1) scanf("%d",&a[i]); a[1]=-inf,a[n+2]=-inf; root=build(0,1,n+2); while(m--) { scanf("%s",str); if(str[0]=='I') //区间插入 { scanf("%d%d",&posi,&tot);posi++; fo(i,1,tot) scanf("%d",&a[i]); x=number(posi),y=number(posi+1); splay(x,0),splay(y,x); int tmp=build(ch[root][1],1,tot); ch[ch[root][1]][0]=tmp; update(ch[ch[root][1]][0]); update(ch[root][1]),update(root); } if(str[0]=='D') //区间删除 { scanf("%d%d",&posi,&tot);posi++; x=number(posi-1),y=number(posi+tot); splay(x,0),splay(y,x); del(ch[ch[root][1]][0]); f[ch[ch[root][1]][0]]=0;ch[ch[root][1]][0]=0; update(ch[root][1]),update(root); } if(str[0]=='M' && str[2]=='K') //区间修改 { scanf("%d%d%d",&posi,&tot,&w);posi++; x=number(posi-1),y=number(posi+tot); splay(x,0),splay(y,x); replace(ch[ch[root][1]][0],w); update(ch[root][1]),update(root); } if(str[0]=='R') //区间翻转 { scanf("%d%d",&posi,&tot);posi++; x=number(posi-1),y=number(posi+tot); splay(x,0),splay(y,x); int tmp=ch[ch[root][1]][0]; rev(tmp); update(ch[root][1]),update(root); } if(str[0]=='G') //区间求和 { scanf("%d%d",&posi,&tot);posi++; x=number(posi-1),y=number(posi+tot); splay(x,0),splay(y,x); pushdown(ch[ch[root][1]][0]); update(ch[root][1]),update(root); printf("%d\n",sum[ch[ch[root][1]][0]]); } if(str[0]=='M' && str[2]=='X') { printf("%d\n",mx[root]); } } return 0;}/*4 31 -1 -5 1 MAX_SUMREVERSE 1 4MAX_SUM*/
0 0
- 洛谷 P2042 维护数列
- bzoj1500/洛谷P2042 维护数列
- BZOJ1500: [NOI2005]维修数列(洛谷P2042)
- 维护数列
- 维护数列
- 【noi2005】维护数列
- [NOI2005] 维护数列 sequence
- 【SPLAY】SPOJ1470维护数列
- 【NOI2005】【splay】维护数列
- 数列维护 NOI2005
- 【SPLAY】NOI2005 维护数列
- 【noi2005】维护数列
- NOI2005维护数列
- noi2005维护数列 splay
- JZOJ2413. 【NOI2005】维护数列
- 【NOI2005】维护数列
- 【NOI2005】维护数列
- Bzoj 1500 维护数列
- Java位移运算符
- 互联网广告综述之点击率特征工程
- RxJava介绍&&Retrofit
- Java动态录入“空心菱形”
- 多选框的相关操作,1.全选,取消全选,2.后端获取多选框的数据
- 洛谷 P2042 维护数列
- 架设wordpress
- python作业3
- Failure delivering result ResultInfo
- 一道经典JS题(关于this)
- NYOJ—一笔画问题(欧拉回路)
- 流媒体-RTSP
- Anne's PHP+MYSQL first step
- 归并排序-逆序对-hdu3743