HDU3487 Play with Chain (Splay)
2014-12-12 20:35
183 查看
题意:给两种操作,一种是切下[a,b]这一段加到c这个位置之后,还有一个翻转[a,b]这个位置,操作过后输出序列。
Splay。。。。虽然理论比较简单,但本渣还是写了一下午+调了3个小时。。。
对于两种操作,切下来的时候就是先把a-1旋转到根,然后把b+1旋转到a-1那个节点的右边,然后b+1这个节点的左子树就是[a,b]的序列了,插入把c旋转到根,c+1旋转到根的右边,然后直接插入到c+1的左子树就好了(这时一定是空的)。。翻转就好像线段树那样,弄个延迟标记就好了。
有很多细节要想清。。。首先,pushup和pushdown的位置要考虑清楚,然后就是注意边界的问题,比如1为左边界,那么我们就是查0这个点了,如果建树只建了1-n就会RE(我RE了几次),所以这里要想清,最后,我居然最后把dfs输出给写错了,导致样例都没过。。。还是太弱了。。。
Splay。。。。虽然理论比较简单,但本渣还是写了一下午+调了3个小时。。。
对于两种操作,切下来的时候就是先把a-1旋转到根,然后把b+1旋转到a-1那个节点的右边,然后b+1这个节点的左子树就是[a,b]的序列了,插入把c旋转到根,c+1旋转到根的右边,然后直接插入到c+1的左子树就好了(这时一定是空的)。。翻转就好像线段树那样,弄个延迟标记就好了。
有很多细节要想清。。。首先,pushup和pushdown的位置要考虑清楚,然后就是注意边界的问题,比如1为左边界,那么我们就是查0这个点了,如果建树只建了1-n就会RE(我RE了几次),所以这里要想清,最后,我居然最后把dfs输出给写错了,导致样例都没过。。。还是太弱了。。。
#include<cstdio> #include<cstring> #include<algorithm> #include<vector> using namespace std; const int MAXN=300010; vector<int> ans; int num[MAXN]; struct Node { Node *ch[2]; Node *fa; int val,mark; int size; }p[MAXN]; Node *null=&p[0]; int tot=0; Node *root=null; //debug部分copy from hh void Treaval(Node *x) { if(x!=null) { Treaval(x->ch[0]); printf("结点%2d:左儿子 %2d 右儿子 %2d 父结点 %2d size = %2d ,key = %2d mark=%d\n",x->val,x->ch[0]->val,x->ch[1]->val,x->fa->val,x->size,x->val,x->mark); Treaval(x->ch[1]); } } void debug() {printf("%d\n",root->val);Treaval(root);} //以上Debug void pushup(Node *rt) { rt->size=1; if(rt->ch[0]!=null) rt->size+=rt->ch[0]->size; if(rt->ch[1]!=null) rt->size+=rt->ch[1]->size; } void pushdown(Node *rt) { if(rt->mark) { rt->ch[0]->mark^=1; rt->ch[1]->mark^=1; rt->mark=0; swap(rt->ch[0],rt->ch[1]); } } void Rotate(Node *x,int c) { Node *y=x->fa; pushdown(y); pushdown(x); y->ch[!c]=x->ch[c]; if(x->ch[c]!=null) x->ch[c]->fa=y; x->fa=y->fa; if(y->fa!=null) { if(y->fa->ch[0]==y) y->fa->ch[0]=x; else y->fa->ch[1]=x; } x->ch[c]=y; y->fa=x; if(y==root) x=root; pushup(y); } void splay(Node *x,Node *f) { if(x==null) return; while(x->fa!=f) { if(x->fa->fa==f) { if(x->fa->ch[0]==x) Rotate(x,1); else Rotate(x,0); } else { Node *y=x->fa,*z=y->fa; if(z->ch[0]==y) { if(y->ch[0]==x) Rotate(y,1),Rotate(x,1); else Rotate(x,0),Rotate(x,1); } else { if(y->ch[1]==x) Rotate(y,0),Rotate(x,0); else Rotate(x,1),Rotate(x,0); } } pushup(x); } } Node *new_Node(int val) { Node *rt=&p[++tot]; rt->ch[0]=rt->ch[1]=rt->fa=null; rt->size=1; rt->mark=0; rt->val=val; return rt; } Node *build(int l,int r) { if(l>r) return null; int mid=(l+r)>>1; Node *rt=new_Node(num[mid]); rt->ch[0]=build(l,mid-1); rt->ch[1]=build(mid+1,r); rt->ch[0]->fa=rt->ch[1]->fa=rt; pushup(rt); return rt; } Node *kth(Node *rt,int k) { pushdown(rt); if(rt->ch[0]->size+1==k) return rt; else if(rt->ch[0]->size>=k) return kth(rt->ch[0],k); else return kth(rt->ch[1],k-rt->ch[0]->size-1); } void solvecut(int a,int b,int c) { Node *L,*R; L=kth(root,a); splay(L,null); R=kth(L,b+2); splay(R,L); Node *root1=R->ch[0]; root1->ch[0]->fa=null; R->ch[0]->fa=null; R->ch[0]=null; Node *LL=kth(L,c+1); Node *RR=kth(L,c+2); splay(LL,null); splay(RR,LL); RR->ch[0]=root1; root1->fa=RR; splay(root1,null); splay(root,null); } void solveflip(int a,int b) { Node *L,*R; L=kth(root,a); splay(L,null); root=L; R=kth(root,b+2); splay(R,L); R->ch[0]->mark^=1; } int flag; void prin(Node *rt) { if(rt==null) return; pushdown(rt); prin(rt->ch[0]); ans.push_back(rt->val); prin(rt->ch[1]); //printf("size=%d val=%d\n",rt->size,rt->val); } int main() { int n,m,i,a,b,c; while(scanf("%d%d",&n,&m)==2) { if(n==-1&&m==-1) break; char op[10]; if(n==1) { scanf("%s",op); if(op[0]=='C') scanf("%*d%*d%*d"); else scanf("%*d%*d"); printf("1\n"); } //null->fa=null->ch[0]=null->ch[1]=null; ans.clear(); tot=0; for(i=0;i<=n+2;i++) num[i]=i; num[n+1]=num[n+2]=0; root=build(0,n+2); //debug(); while(m--) { scanf("%s",op); if(op[0]=='C') { scanf("%d%d%d",&a,&b,&c); solvecut(a,b,c); //debug(); } else { scanf("%d%d",&a,&b); solveflip(a,b); } } flag=1; prin(root); //debug(); for(i=0;i<ans.size();i++) { if(ans[i]==0) continue; if(flag) printf("%d",ans[i]); else printf(" %d",ans[i]); flag=0; } printf("\n"); } return 0; }
相关文章推荐
- HDU3487 Play with Chain(Splay)
- hdu3487 Play with Chain(Splay)
- hdu3487 Play with Chain 伸展树splay
- 【hdu3487】【splay】Play with Chain
- hdu3487 Play with Chain(splay)
- hdu3487 Play with Chain splay
- hdu3487 Play with Chain (Splay)
- 【HDU3487】【splay分裂合并】Play with Chain
- Splay树(区间添加删除 | 区间翻转)——HDU 3487 Play with Chain
- HDU 3487 Play with Chain | Splay
- Splay 模板题 一 hdu 3487 play with chain
- Hdu3487-Play with Chain(伸展树分裂合并)
- hdu 3487 Play with Chain splay tree
- hdu3487 Play with Chain
- hdu 3487 Play with Chain(Splay)
- HDU - 3487 Play with Chain __ Splay
- HDU 3487 Play with Chain 伸展树splay
- HDU 3487 Play with Chain(Splay 经典操作)
- 【HDU】3487 Play with Chain 【splay】
- HDU 3478 Play with Chain (Splay树)