# 【dfs序】【二分】【主席树】【分块】bzoj3351 [ioi2009]Regions

http://dzy493941464.sinaapp.com/archives/96

#include<cstdio>
#include<set>
#include<vector>
#include<cmath>
#include<algorithm>
using namespace std;
int f,C;
void R(int &x){
C=0;f=1;
for(;C<'0'||C>'9';C=getchar())if(C=='-')f=-1;
for(x=0;C>='0'&&C<='9';C=getchar())(x*=10)+=(C-'0');
x*=f;
}
void P(int x){
if(x<10)putchar(x+'0');
else{P(x/10);putchar(x%10+'0');}
}
typedef double db;
#define N 200001
vector<int>Over,Nodes[N],col_in_sub[N];
typedef vector<int>::iterator ER;
int v[N],next[N],first[N],en,sz;
{
v[++en]=V;
next[en]=first[U];
first[U]=en;
}
multiset<int>S;
int anss[701][701];
int n,K,m,a[N],Ls[N],Rs[N],pl[N];
int root[N],e;
struct Node{int v,lc,rc;}T[N*24];
void Insert(int pre,int cur,int p,int l,int r)
{
if(l==r)
{
T[cur].v=T[pre].v+1;
return;
}
int m=(l+r>>1);
if(p<=m)
{
T[cur].lc=++e; T[cur].rc=T[pre].rc;
Insert(T[pre].lc,T[cur].lc,p,l,m);
}
else
{
T[cur].rc=++e; T[cur].lc=T[pre].lc;
Insert(T[pre].rc,T[cur].rc,p,m+1,r);
}
T[cur].v=T[T[cur].lc].v+T[T[cur].rc].v;
}
int Query(int cur,int p,int l,int r)
{
if(l==r) return T[cur].v;
int m=(l+r>>1);
if(p<=m) return Query(T[cur].lc,p,l,m);
else return Query(T[cur].rc,p,m+1,r);
}
int fa[N],id[N];
void dfs(int U)
{
root[U]=++e;
Insert(root[fa[U]],root[U],a[U],1,K);
Ls[U]=++en;
if(pl[a[U]]>sz)
for(ER it=Over.begin();it!=Over.end();++it)
anss[id[*it]][id[a[U]]]+=S.count(*it);
S.insert(a[U]);
for(int i=first[U];i;i=next[i])
dfs(v[i]);
Rs[U]=en;
S.erase(S.find(a[U]));
}
int main()
{
int x,y;
R(n); R(K); R(m);
sz=K*K/m;
R(a[1]); ++pl[a[1]];
for(int i=2;i<=n;++i)
{
R(x); R(a[i]);
fa[i]=x;
++pl[a[i]];
}
en=0;
for(int i=1;i<=n;++i)
{
if(pl[i]>sz)
{
if(!id[i]) id[i]=++en;
Over.push_back(i);
}
if(pl[a[i]]<=sz) Nodes[a[i]].push_back(i);
}
en=0; dfs(1);
for(int i=1;i<=n;++i) col_in_sub[a[i]].push_back(Ls[i]);
for(int i=1;i<=n;++i) sort(col_in_sub[i].begin(),col_in_sub[i].end());
for(;m;--m)
{
R(x); R(y);
if(pl[x]>sz&&pl[y]>sz) P(anss[id[x]][id[y]]),puts("");
else if(pl[x]<=sz)
{
int ans=0;
for(ER it=Nodes[x].begin();it!=Nodes[x].end();++it) if(Ls[*it]!=Rs[*it])
ans+=(upper_bound(col_in_sub[y].begin(),col_in_sub[y].end(),Rs[*it])-
lower_bound(col_in_sub[y].begin(),col_in_sub[y].end(),Ls[*it]+1));
P(ans); puts("");
}
else
{
int ans=0;
for(ER it=Nodes[y].begin();it!=Nodes[y].end();++it)
ans+=Query(root[fa[*it]],x,1,K);
P(ans); puts("");
}
}
return 0;
}
posted @ 2015-04-22 08:07  AutSky_JadeK  阅读(303)  评论(0编辑  收藏  举报