Xqbk @ 2021-05-19 20:54:39
现象是节点的son没有成功连接到被翻转的子树(?)
#include<iostream>
#include<cstdio>
using namespace std;
const int MAXN=100005;
const int INF=1e9;
int n,m;
int rt,tot;
struct Splay
{
int fa,son[2],siz,cnt,val,rev;
}s[MAXN];
void pushup(int x)
{
s[x].siz=s[s[x].son[0]].siz+s[s[x].son[1]].siz+s[x].cnt;
}
void pushdown(int x)
{
if(x&&s[x].rev)
{
s[s[x].son[0]].rev^=1;
s[s[x].son[1]].rev^=1;
swap(s[s[x].son[0]],s[s[x].son[1]]);
s[x].rev=0;
}
}
bool get(int x)
{
return x==s[s[x].fa].son[1];
}
void rotate(int x)
{
int y=s[x].fa;
int z=s[y].fa;
pushdown(x);
pushdown(y);
int d=get(x);
s[y].son[d]=s[x].son[d^1];
if(s[x].son[d^1])s[s[x].son[d^1]].fa=y;
s[x].son[d^1]=y;
s[y].fa=x;
s[x].fa=z;
if(z)s[z].son[y==s[z].son[1]]=x;
pushup(y);
pushup(x);
}
void splay(int x,int k)
{
for(int f=s[x].fa;f=s[x].fa,f!=k;rotate(x))
{
if(s[f].fa!=k)rotate(get(x)==get(f)?f:x);
}
if(!k)
{
rt=x;
}
}
void ins(int k)
{
if(!rt)
{
s[++tot].val=k;
s[tot].cnt++;
rt=tot;
pushup(rt);
return;
}
int cur=rt;
int f=0;
while(1)
{
if(s[cur].val==k)
{
s[cur].cnt++;
pushup(cur);
pushup(f);
splay(cur,0);
break;
}
f=cur;
cur=s[cur].son[s[cur].val<k];
if(!cur)
{
s[++tot].val=k;
s[tot].cnt++;
s[tot].fa=f;
s[f].son[s[f].val<k]=tot;
pushup(tot);
pushup(f);
splay(tot,0);
break;
}
}
}
int find(int k)
{
int cur=rt;
while(1)
{
pushdown(cur);
if(s[cur].son[0]&&k<=s[s[cur].son[0]].siz)
{
cur=s[cur].son[0];
}
else
{
k-=s[cur].cnt+s[s[cur].son[0]].siz;
if(k<=0)
{
splay(cur,0);
return cur;
}
cur=s[cur].son[1];
}
}
}
void dfs(int cur)
{
pushdown(cur);
if(s[cur].son[0])
{
dfs(s[cur].son[0]);
}
if(s[cur].val!=INF&&s[cur].val!=-INF)
{
cout<<s[cur].val<<' ';
}
if(s[cur].son[1])
{
dfs(s[cur].son[1]);
}
return;
}
void reverse(int l,int r)
{
int x=find(l-1);
int y=find(r+1);
splay(x,0);
splay(y,x);
int cur=s[rt].son[1];
cur=s[cur].son[0];
s[cur].rev^=1;
}
int main()
{
cin>>n>>m;
ins(-INF);
ins(INF);
for(int i=1;i<=n;i++)
{
ins(i);
}
for(int i=1;i<=m;i++)
{
int l,r;
cin>>l>>r;
reverse(l+1,r+1);
}
dfs(rt);
}
by 阿丑 @ 2021-05-19 21:31:09
@Xqbk 好像把 pushdown
里的 swap(s[s[x].son[0]],s[s[x].son[1]]);
写成 swap(s[x].son[0],s[x].son[1]);
就能过样例了,但我不知道为什么
by 阿丑 @ 2021-05-19 21:37:52
哦,如果 swap
把 s[0]
换成有权值的节点的话就会出现非常灵异的现象。
另,我感觉为了确保复杂度正确,应该在 splay
里先 pushdown
吧,不然的话方向应该不确定。
by Xqbk @ 2021-05-20 21:25:50
@阿丑 感谢,过了
但是测试了一下splay
里面有没有pushdown
好像没发现区别