记录编号 460857 评测结果 AAAAAAAAAA
题目名称 [ZJOI 2004] 树的果实 最终得分 100
用户昵称 GravatarHzoi_Mafia 是否通过 通过
代码语言 C++ 运行时间 9.280 s
提交时间 2017-10-18 17:47:21 内存使用 5.65 MiB
显示代码纯文本
#include <iostream>
#include <cstring>
#include <cstdlib>
#include <cstdio>
using namespace std;
inline int read(){
	int sum(0);
	char ch(getchar());
	for(;ch<'0'||ch>'9';ch=getchar());
	for(;ch>='0'&&ch<='9';sum=sum*10+(ch^48),ch=getchar());
	return sum;
}
struct edge{
	int e;
	edge *n;
}*pre[100005];
inline void insert(int s,int e){
	edge *tmp(new edge);
	tmp->e=e;tmp->n=pre[s];pre[s]=tmp;
}
#define get_size(x) (x?x->size:0)
struct node{
	node *lch,*rch;
	int key,fix,size;
	node(int x=0):lch(NULL),rch(NULL),size(1),fix(rand()),key(x){}
	inline void pushup(){this->size=get_size(this->lch)+get_size(this->rch)+1;}
}*tr[400005];
inline void left_rotate(node *&x){
	node *tmp(x->rch);
	x->rch=tmp->lch;
	tmp->lch=x;
	x->pushup();
	tmp->pushup();
	x=tmp;
}
inline void right_rotate(node *&x){
	node *tmp(x->lch);
	x->lch=tmp->rch;
	tmp->rch=x;
	x->pushup();
	tmp->pushup();
	x=tmp;
}
inline void insert(node *&x,int v){
	if(!x){
		x=new node(v);
		return;
	}
	if(v<=x->key){
		insert(x->lch,v);
		x->pushup();
		if(x->lch->fix<x->fix)
			right_rotate(x);
	}
	else{
		insert(x->rch,v);
		x->pushup();
		if(x->rch->fix<x->fix)
			left_rotate(x);
	}
}
inline int qmax(node *now,int x){
	int ret(0);
	while(now){
		if(x>=now->key)now=now->rch;
		else ret+=get_size(now->rch)+1,now=now->lch;
	}
	return ret;
}
int n;
int w[100005];
int fa[100005],son[100005],size[100005],dep[100005];
inline void dfs1(int u){
	size[u]=1;son[u]=0;
	for(edge *i=pre[u];i;i=i->n){
		int e(i->e);
		if(e==fa[u])continue;
		fa[e]=u;
		dep[e]=dep[u]+1;
		dfs1(e);
		size[u]+=size[e];
		if(size[e]>size[son[u]])son[u]=e;
	}
}
int cnt;
int l[100005],r[100005],pos[100005],top[100005];
inline void dfs2(int u,int rt){
	top[u]=rt;
	l[u]=++cnt;
	pos[cnt]=u;
	if(son[u])dfs2(son[u],rt);
	for(edge *i=pre[u];i;i=i->n){
		int e(i->e);
		if(e==fa[u]||e==son[u])continue;
		dfs2(e,e);
	}
	r[u]=cnt;
}
inline void build(int l,int r,int rt){
	for(int i=l;i<=r;++i)insert(tr[rt],w[pos[i]]);
	if(l==r)return;
	int mid((l+r)>>1);
	build(l,mid,rt<<1);build(mid+1,r,rt<<1|1);
}
inline int qmax(int ll,int rr,int x,int l,int r,int i){
	if(ll<=l&&r<=rr)return qmax(tr[i],x);
	int mid((l+r)>>1),ret(0);
	if(ll<=mid)ret+=qmax(ll,rr,x,l,mid,i<<1);
	if(mid<rr)ret+=qmax(ll,rr,x,mid+1,r,i<<1|1);
	return ret;
}
inline int query(int x,int y,int w){
	int ret(0);
	while(top[x]^top[y]){
		if(dep[top[x]]<dep[top[y]])swap(x,y);
		ret+=qmax(l[top[x]],l[x],w,1,n,1);
		x=fa[top[x]];
	}
	if(dep[x]>dep[y])swap(x,y);
	ret+=qmax(l[x],l[y],w,1,n,1);
	return ret;
}
int main(){
	freopen("treesfruits.in","r",stdin);
	freopen("treesfruits.out","w",stdout);
	n=read();
	for(int i=2;i<=n;++i){
		int x(read());
		insert(x,i);
	}
	for(int i=1;i<=n;++i)w[i]=read();
	dfs1(1);dfs2(1,1);
	build(1,n,1);
	for(int i=1;i<=n;++i)printf("%d %d %d\n",qmax(l[i],r[i],w[i],1,n,1),i==1?0:(qmax(1,l[i]-1,w[i],1,n,1)+qmax(r[i]+1,n,w[i],1,n,1)),query(1,i,w[i]));
}