3159: 决战
题解:
这个有利用比较好的理解lct。。
但是呀这里你思路理清楚了也不好写。。
细节挺多的
关键是非常难调。。。
代码:
#include <bits/stdc++.h> using namespace std; #define rint register int #define IL inline #define rep(i,h,t) for (int i=h;i<=t;i++) #define dep(i,t,h) for (int i=t;i>=h;i--) #define me(x) memset(x,0,sizeof(x)) #define ll long long #define mep(x) memcpy(x,y,sizeof(y)) #define mid ((h+t)>>1) namespace IO{ char ss[1<<24],*A=ss,*B=ss; IL char gc() { return A==B&&(B=(A=ss)+fread(ss,1,1<<24,stdin),A==B)?EOF:*A++; } template<class T>void read(T &x) { rint f=1,c; while (c=gc(),c<48||c>57) if (c=='-') f=-1; x=(c^48); while (c=gc(),c>47&&c<58) x=(x<<3)+(x<<1)+(c^48); x*=f; } IL void read2(string &x) { rint f=1,c; while (c=gc(),!(('A'<=c&&c<='Z')||('a'<=c&&c<='z'))); x=c; while (c=gc(),(('A'<=c&&c<='Z')||('a'<=c&&c<='z'))) {char c1=c; x+=c1; } } char sr[1<<24],z[20]; int Z,C=-1; template<class T>void wer(T x) { if (x<0) sr[++C]='-',x=-x; while (z[++Z]=x%10+48,x/=10); while (sr[++C]=z[Z],--Z); } IL void wer1() {sr[++C]=' ';} IL void wer2() {sr[++C]='\n';} template<class T>IL void maxa(T &x,T y) { if (x<y) x=y;} template<class T>IL void mina(T &x,T y) { if (x>y) x=y;} template<class T>IL T MAX(T x,T y) {return x>y?x:y;} template<class T>IL T MIN(T x,T y) {return x<y?x:y;} }; using namespace IO; const int N=6e4; const int INF=1e9; struct re{ ll a,b,c; }e[N*2]; int l,head[N]; IL void arr(int x,int y) { e[++l].a=head[x]; e[l].b=y; head[x]=l; } struct Splay{ bool rev[N]; int ls[N],rs[N],fa[N],num[N],ma[N],v[N],na[N],dy[N],lazy[N]; ll sum[N]; Splay() {rep(i,0,N-1) num[i]=0; na[0]=INF;} IL void down(int x) { if (ls[x]) { if (rev[x]) { swap(ls[ls[x]],rs[ls[x]]); rev[ls[x]]^=1; } if (lazy[x]) { lazy[ls[x]]+=lazy[x]; v[ls[x]]+=lazy[x]; sum[ls[x]]+=1ll*num[ls[x]]*lazy[x]; ma[ls[x]]+=lazy[x]; na[ls[x]]+=lazy[x]; } } if (rs[x]) { if (rev[x]) { swap(ls[rs[x]],rs[rs[x]]); rev[rs[x]]^=1; } if (lazy[x]) { lazy[rs[x]]+=lazy[x]; v[rs[x]]+=lazy[x]; sum[rs[x]]+=1ll*num[rs[x]]*lazy[x]; ma[rs[x]]+=lazy[x]; na[rs[x]]+=lazy[x]; } } rev[x]=lazy[x]=0; } IL void updata(int x) { sum[x]=v[x]+sum[ls[x]]+sum[rs[x]]; ma[x]=MAX(v[x],MAX(ma[ls[x]],ma[rs[x]])); na[x]=MIN(v[x],MIN(na[ls[x]],na[rs[x]])); num[x]=num[ls[x]]+num[rs[x]]+1; } IL void push_rev(int x) { rev[x]^=1; swap(ls[x],rs[x]); } IL bool pd(int x) { return ls[fa[x]]==x||rs[fa[x]]==x; } void rotate(int x,int y) { int f1=fa[x]; if (y==1) { rs[f1]=ls[x]; if (rs[f1]) fa[rs[f1]]=f1; } else { ls[f1]=rs[x]; if (ls[f1]) fa[ls[f1]]=f1; } fa[x]=fa[f1]; if (pd(f1)) { if (ls[fa[f1]]==f1) ls[fa[x]]=x; else rs[fa[x]]=x; } fa[f1]=x; if (y==1) ls[x]=f1; else rs[x]=f1; updata(f1); updata(x); } int dfs(int x) { int ans=x; if (pd(x)) ans=dfs(fa[x]); down(x); return ans; } void splay(int x) { int k=dfs(x); dy[x]=dy[k]; int f1=fa[x]; while (pd(x)) { if (!pd(fa[x])) if (ls[f1]==x) rotate(x,2); else rotate(x,1); else if (ls[fa[f1]]==f1) if (ls[f1]==x) rotate(f1,2),rotate(x,2); else rotate(x,1),rotate(x,2); else if (rs[f1]==x) rotate(f1,1),rotate(x,1); else rotate(x,2),rotate(x,1); f1=fa[x]; } } int find(int x,int k) { splay(x); while (1) { down(x); if (num[ls[x]]+1==k) return(x); if (num[ls[x]]+1<k) k-=num[ls[x]]+1,x=rs[x]; else x=ls[x]; } } }S1,S2; struct lct{ IL int pos(int x) { return S2.find(S1.dy[x],S1.num[S1.ls[x]]+1); } void access(int x) { int x2; for (int y1=0,y2=0;x;x=S1.fa[x]) { S1.splay(x); x2=pos(x); S2.splay(x2); if (S1.rs[x]) S1.dy[S1.rs[x]]=S2.rs[x2]; S1.dy[x]=x2; S1.rs[x]=y1; S2.rs[x2]=y2; if (y2) S2.fa[y2]=x2; S1.updata(x); S2.updata(x2); y1=x; y2=x2; } } IL int gao2(int x) { access(x); S1.splay(x); int x2=pos(x); S2.splay(x2); return x2; } void mkr(int x) { int x2=gao2(x); S1.push_rev(x); S2.push_rev(x2); } void split(int x,int y) { mkr(x); gao2(y); } re query(int x,int y) { S1.splay(y); int k=pos(y); split(x,y); return (re){S2.sum[k],S2.ma[k],S2.na[k]}; } void change(int x,int y,int z) { S1.splay(y); int k=pos(y); split(x,y); S2.sum[k]+=1ll*z*S2.num[k]; S2.v[k]+=z; S2.ma[k]+=z; S2.na[k]+=z; S2.lazy[k]+=z; } void reverse(int x,int y) { S1.splay(y); int k=pos(y); split(x,y); S2.push_rev(k); } }L; void dfs(int x,int y) { S1.fa[x]=y; S2.fa[x]=y; S1.dy[x]=x; for(rint u=head[x];u;u=e[u].a) { int v=e[u].b; if (v!=y) dfs(v,x); } } int main() { freopen("1.in","r",stdin); freopen("1.out","w",stdout); int n,m,Q; read(n); read(m); read(Q); rep(i,1,n-1) { int x,y; read(x); read(y); arr(x,y); arr(y,x); } dfs(Q,0); rep(i,1,m) { int x,y,z; string s; read2(s); ll ans; if(s[0]=='I'&&s[2]=='c') { read(x); read(y); read(z); L.change(x,y,z); } else { read(x); read(y); if (s[0]=='S') { ans=L.query(x,y).a; wer(ans); wer2(); } if (s[1]=='a') { ans=L.query(x,y).b; wer(ans); wer2(); } if (s[1]=='i') { ans=L.query(x,y).c; wer(ans); wer2(); } if (s[0]=='I') { L.reverse(x,y); } } } fwrite(sr,1,C+1,stdout); return 0; }