bzoj2631

非常好的一篇博客(LCT)

题解来源(LCT)

先抄了一遍板子【注意数据范围】

#include<cstdio>
#include<cctype>
#include<algorithm>
#define ls tr[x][0]
#define rs tr[x][1]
#define ui unsigned int
using namespace std;
const ui maxn=100004,mod=51061;
ui n,q,fa[maxn],tr[maxn][2],siz[maxn],sum[maxn],val[maxn],ad[maxn],mul[maxn],tmp[maxn];
bool rev[maxn];
inline bool isroot(int x){return tr[fa[x]][0]==x || tr[fa[x]][1]==x;}
inline void pushup(int x){sum[x]=(val[x]+sum[ls]+sum[rs])%mod;siz[x]=1+siz[ls]+siz[rs];}
inline void pushr(int x){swap(ls,rs);rev[x]^=1;}
inline void _add(int x,int inc){val[x]=(val[x]+inc)%mod;ad[x]=(ad[x]+inc)%mod;(inc*=siz[x])%=mod;sum[x]=(sum[x]+inc)%mod;}
inline void _mul(int x,int ml){sum[x]=(sum[x]*ml)%mod;val[x]=(val[x]*ml)%mod;ad[x]=(ad[x]*ml)%mod;mul[x]=(mul[x]*ml)%mod;}
inline void pushdown(int x){
    if(mul[x]!=1)_mul(ls,mul[x]),_mul(rs,mul[x]),mul[x]=1;
    if(ad[x])_add(ls,ad[x]),_add(rs,ad[x]),ad[x]=0;
    if(rev[x]){if(ls)pushr(ls);if(rs)pushr(rs);rev[x]=0;}
}
inline void read(ui &x){
    char ch=getchar();x=0;int f=1;
    while(!isdigit(ch)){if(ch=='-')f=-1;ch=getchar();}
    while(isdigit(ch)){x=(x<<1)+(x<<3)+ch-'0';ch=getchar();}
    x*=f;
}
inline void read(int &x){
    char ch=getchar();x=0;int f=1;
    while(!isdigit(ch)){if(ch=='-')f=-1;ch=getchar();}
    while(isdigit(ch)){x=(x<<1)+(x<<3)+ch-'0';ch=getchar();}
    x*=f;
}
inline void rotate(int x){
    int f=fa[x],gfa=fa[f],whicx=tr[f][1]==x,flag=isroot(f);
    tr[f][whicx]=tr[x][whicx^1];if(tr[f][whicx])fa[tr[f][whicx]]=f;
    tr[x][whicx^1]=f;fa[f]=x;
    fa[x]=gfa;if(flag)tr[gfa][tr[gfa][1]==f]=x;
    pushup(f);pushup(x);
}

inline void splay(int x){
    int f,gf,head=0,y=x;tmp[++head]=y;
    while(isroot(y))tmp[++head]=y=fa[y];
    while(head)pushdown(tmp[head--]);
    while(isroot(x)){
        f=fa[x];gf=fa[f];
        if(isroot(f))rotate((tr[f][1]==x)==(tr[gf][1]==f)?f:x);
        rotate(x);
    }
}
inline void access(int x){for(int y=0;x;x=fa[y=x])splay(x),rs=y,pushup(x);}
inline void makeroot(int x){access(x);splay(x);pushr(x);}
inline void split(int x,int y){makeroot(x);access(y);splay(y);}
inline void link(int x,int y){makeroot(x);fa[x]=y;}
inline void cut(int x,int y){split(x,y);fa[x]=tr[y][0]=0;pushup(y);}
inline void ada(int a,int b,int val){split(a,b);_add(b,val);}
inline void mu(int a,int b,int val){split(a,b);_mul(b,val);}
int main(){
    char ch[10];
    read(n);read(q);
    int a,b,c,d;
    for(int i=1;i<=n;i++)sum[i]=val[i]=mul[i]=1;
    for(int i=1;i<n;i++)read(a),read(b),link(a,b);
    while(q--){
        scanf("%s",ch);
        switch(ch[0]){
            case'+':read(a);read(b);read(c);ada(a,b,c);break;
            case'-':read(a);read(b);read(c);read(d);cut(a,b);link(c,d);break;
            case'/':read(a);read(b);split(a,b);printf("%d\n",sum[b]);break;
            case'*':read(a);read(b);read(c);mu(a,b,c);
        }
    }
}

 

posted @ 2018-05-23 22:19  lnyzo  阅读(166)  评论(0编辑  收藏  举报