# BZOJ_3786_星系探索_splay维护出栈入栈序

BZOJ_3786_星系探索_splay维护出栈入栈序

## Input

(1)"Q di"表示小C要开始一次实验,收集器的初始位置在星球di.

(2)"C xi yi"表示星球xi的依赖星球变为了星球yi.

(3)"F pi qi"表示星球pi能量激发，常数为qi.

3
1
1
4 5 7
5
Q 2
F 1 3
Q 2
C 2 3
Q 2

9
15
25

## HINT

n<=100000,m<=300000,1<di,xi<=n,wi,qi<=100000.保证操作合法。注意w_i>=0

#include <cstdio>
#include <cstring>
#include <algorithm>
using namespace std;
typedef long long ll;
#define N 200050
#define ls ch[p][0]
#define rs ch[p][1]
#define get(x) (ch[f[x]][1]==x)
int zc[N],fc[N],a[N],type[N],val[N],w[N],fa[N];
ll sum[N];
int del[N];
char pbuf[100000],*pp=pbuf;
__attribute__((optimize("-O3")))void push(const char ch) {
if(pp-pbuf==100000) fwrite(pbuf,1,100000,stdout),pp=pbuf;
*pp++=ch;
}
__attribute__((optimize("-O3")))void write(ll x) {
static int sta[50];
int top=0;
do{sta[++top]=x%10,x/=10;}while(x);
while(top) push(sta[top--]+'0');
push('\n');
}
__attribute__((optimize("-O3")))inline char nc() {
static char buf[100000],*p1,*p2;
}
__attribute__((optimize("-O3")))int rd() {
int x=0; char s=nc();
while(s<'0'||s>'9') s=nc();
while(s>='0'&&s<='9') x=(x<<3)+(x<<1)+s-'0',s=nc();
return x;
}
__attribute__((optimize("-O3")))char rc() {
char s=nc();
while(s!='Q'&&s!='C'&&s!='F') s=nc();
return s;
}
__attribute__((optimize("-O3")))void give(int p,int v) {
val[p]+=v; del[p]+=v; sum[p]+=1ll*(zc[p]-fc[p])*v;
}
__attribute__((optimize("-O3")))void pushup(int p) {
if(!p) return ;
siz[p]=1;
zc[p]=fc[p]=0;
if(type[p]==1) zc[p]=1;
else if(type[p]==-1) fc[p]=1;
sum[p]=val[p]*type[p];
siz[p]+=siz[ls],sum[p]+=sum[ls],zc[p]+=zc[ls],fc[p]+=fc[ls];
siz[p]+=siz[rs],sum[p]+=sum[rs],zc[p]+=zc[rs],fc[p]+=fc[rs];
}
__attribute__((optimize("-O3")))void pushdown(int p) {
if(del[p]) {
if(ls) give(ls,del[p]);
if(rs) give(rs,del[p]);
del[p]=0;
}
}
__attribute__((optimize("-O3")))void rotate(int x) {
int y=f[x],z=f[y],k=get(x);
ch[y][k]=ch[x][!k]; f[ch[y][k]]=y;
ch[x][!k]=y; f[y]=x; f[x]=z;
if(z) ch[z][ch[z][1]==y]=x;
if(rt==y) rt=x;
pushup(y); pushup(x);
}
__attribute__((optimize("-O3")))void update(int p,int y) {
if(f[p]!=y) update(f[p],y);
pushdown(p);
}
__attribute__((optimize("-O3")))void splay(int x,int y) {
update(x,y);
for(int d;(d=f[x])!=y;rotate(x))
if(f[d]!=y)
rotate(get(x)==get(d)?d:x);
}
__attribute__((optimize("-O3")))inline void add(int u,int v) {
}
__attribute__((optimize("-O3")))void dfs(int x) {
int i;a[++tot]=x; type[tot+1]=1; dfn[x]=tot+1; val[tot+1]=w[x];
f[to[i]]=x;
dfs(to[i]);
}
a[++tot]=x; type[tot+1]=-1; son[x]=tot+1; val[tot+1]=w[x];
}
__attribute__((optimize("-O3")))void build(int fa,int l,int r) {
if(l>r) return ;
int mid=(l+r)>>1;
f[mid]=fa;
ch[fa][mid>fa]=mid;
build(mid,l,mid-1);
build(mid,mid+1,r);
pushup(mid);
}
__attribute__((optimize("-O3")))int pre() {
int p=ch[rt][0];
for(;rs;p=rs) pushdown(p);
return p;
}
__attribute__((optimize("-O3")))int suc() {
int p=ch[rt][1];
for(;ls;p=ls) pushdown(p);
return p;
}
__attribute__((optimize("-O3")))void huan(int x,int y) {
splay(dfn[x],0); int p2=pre();
splay(son[x],0); int p4=suc();
splay(p2,0); splay(p4,p2);
int p5=ch[p4][0]; f[p5]=0; ch[p4][0]=0;
pushup(p4); pushup(p2);
int p6=dfn[y];
splay(p6,0); int p7=suc();
splay(p7,p6);
ch[p7][0]=p5; f[p5]=p7;
pushup(p5); pushup(p7); pushup(p6);
}
__attribute__((optimize("-O3")))int find(int x) {
int p=rt;
while(1) {
pushdown(p);
if(x<=siz[ls]) p=ls;
else {
x-=siz[ls]+1;
if(!x) return p;
p=rs;
}
}
}
__attribute__((optimize("-O3")))void print() {
int i,p;
for(i=1;i<=tot+2;i++) {
p=find(i);
printf("i=%d,p=%d,val[p]=%d,f[p]=%d,zc[p]=%d,fc[p]=%d\n",i,p,val[p],f[p],zc[p],fc[p]);
}
}
__attribute__((optimize("-O3")))int main() {
n=rd();
register int i,x,y,p;
for(i=2;i<=n;i++) {
x=rd();
}
for(i=1;i<=n;i++) w[i]=rd();
dfs(1);
build(0,1,tot+2);
rt=(tot+3)>>1;
m=rd();
char opt;
while(m--) {
opt=rc(); x=rd();
if(opt=='Q') {
x=dfn[x];
// splay(x,0); p=suc();
// splay(1,0); splay(p,1);
splay(1,0);
splay(x,1);
for(p=ch[x][1];ls;p=ls);
splay(p,1);
write(sum[ls]);
}else if(opt=='C') {
y=rd();
// scanf("%d",&y);
if(fa[x]!=y) huan(x,y),fa[x]=y;
}else {
y=rd();
// scanf("%d",&y);
int q=dfn[x];
splay(q,0); p=pre();
int t1=p;
q=son[x];
splay(q,0); p=suc();
splay(t1,0); splay(p,t1);
give(ls,y);
}
}
fwrite(pbuf,1,pp-pbuf,stdout);
}


posted @ 2018-06-28 18:27  fcwww  阅读(186)  评论(0编辑  收藏  举报