Chain tree split and the LCT (continued)

include

include

define N 110000

define mod 51061

using namespace std;
typedef long long LL;
struct node
{
LL son[2],f,c,sum,size,la1,la2;bool sv;
}tr[N];
inline LL chk(LL x){return tr[tr[x].f].son[1]==x;}
inline bool nroot(LL x){return tr[tr[x].f].son[0]==x || tr[tr[x].f].son[1]==x;}
inline LL update(LL x){tr[x].sum=(tr[tr[x].son[0]].sum+tr[tr[x].son[1]].sum+tr[x].c)%mod;tr[x].size=tr[tr[x].son[0]].size+tr[tr[x].son[1]].size+1;}
inline void rotate(LL x)
{
LL f=tr[x].f,ff=tr[f].f,w=chk(x)^1,son=tr[x].son[w];
LL r,R;
r=son;R=f;tr[r].f=R;tr[R].son[w^1]=r;
r=x;R=ff;tr[r].f=R;if(nroot(f))tr[R].son[chk(f)]=r;
r=f;R=x;tr[r].f=R;tr[R].son[w]=r;
update(f);update(x);
}
//先乘后加
inline void jia(LL x,LL d){tr[x].la1+=d;tr[x].la1%=mod;}
inline void cheng(LL x,LL d){tr[x].la1=d;tr[x].la2=d;tr[x].la1%=mod;tr[x].la2%=mod;}
void pushdown(LL x)
{
if(tr[x].sv)
{
tr[x].sv=0;
tr[x].son[0]^=tr[x].son[1]^=tr[x].son[0]^=tr[x].son[1];
tr[tr[x].son[0]].sv^=1;tr[tr[x].son[1]].sv^=1;
}
if(tr[x].la2!=1)
{
tr[x].sum=tr[x].la2;tr[x].c=tr[x].la2;tr[x].sum%=mod;tr[x].c%=mod;
cheng(tr[x].son[0],tr[x].la2);cheng(tr[x].son[1],tr[x].la2);
tr[x].la2=1;
}
if(tr[x].la1)
{
tr[x].sum+=tr[x].la1*tr[x].size;tr[x].c+=tr[x].la1;
tr[x].sum%=mod;tr[x].c%=mod;
jia(tr[x].son[0],tr[x].la1);jia(tr[x].son[1],tr[x].la1);
tr[x].la1=0;
}
}
LL sta[N],len;
inline void splay(LL x)
{
LL y=x;len=0;
if(tr[x].son[0])sta[++len]=tr[x].son[0];
if(tr[x].son[1])sta[++len]=tr[x].son[1];
sta[++len]=x;
while(nroot(y))
{
LL w=chk(y)^1;y=tr[y].f;
if(tr[y].son[w])sta[++len]=tr[y].son[w];
sta[++len]=y;
}
while(len)pushdown(sta[len--]);
while(nroot(x))
{
LL f=tr[x].f,ff=tr[f].f;
if(!nroot(f))rotate(x);
else rotate(chk(x)^chk(f)?x:f),rotate(x);
}
}
inline void ace(LL x)
{
for(LL y=0;x;x=tr[y=x].f)splay(x),tr[x].son[1]=y,update(x);
}
inline LL findroot(LL x)
{
ace(x);splay(x);
LL y=x;while(tr[y].son[0])y=tr[y].son[0],pushdown(y);
return y;
}
inline void makeroot(LL x)
{
ace(x);splay(x);
tr[x].sv^=1;
}
inline void link(LL x,LL y)
{
makeroot(x);tr[x].f=y;
}
inline void spilt(LL x,LL y)
{
makeroot(x);
ace(y);splay(x);
}
inline void cut(LL x,LL y)
{
spilt(x,y);
tr[x].son[1]=0;tr[y].f=0;update(x);
}
LL n,m;
int main()
{
scanf("%lld%lld",&n,&m);
for(LL i=1;i<=n;i++)tr[i].c=tr[i].sum=1,tr[i].la2=1,tr[i].size=1;
for(LL i=1;i<n;i++)
{
LL x,y;scanf("%lld%lld",&x,&y);
link(x,y);
}
for(LL i=1;i<=m;i++)
{
LL tt,x,y;scanf("%lld%lld%lld",&tt,&x,&y);
if(tt==1)
{
LL c;scanf("%lld",&c);
spilt(x,y);
jia(x,c);
}
else if(tt==2)
{
LL c;scanf("%lld",&c);
spilt(x,y);
cheng(x,c);
}
else if(tt==3)
{
cut(x,y);scanf("%lld%lld",&x,&y);
link(x,y);
}
else
{
spilt(x,y);
printf("%lld\n",tr[x].sum);
}
}
return 0;
}

Guess you like

Origin www.cnblogs.com/zhangjianjunab/p/11361949.html