码迷,mamicode.com
首页 > 其他好文 > 详细

线段树合并

时间:2019-08-28 01:35:23      阅读:97      评论:0      收藏:0      [点我收藏+]

标签:https   size   mes   turn   线段树   void   using   bzoj   val   

 https://blog.csdn.net/keydou/article/details/83691189

 bzoj 4756

题目大意:给出一棵树(根为 1),每个点有点权,对于每个点,询问它子树中点权比它大的点的个数

其实可以把这道题当成线段树合并入门题来做

首先把点权离散化,把所有的点都先单独建一颗权值线段树

然后从根开始 dfs ,一边 dfs 一边合并线段树,不断合并上去,最后求答案就行了

#include<cstdio>
#include<cstring>
#include<algorithm>
#define N 100005
using namespace std;
int n,m,t,tot;
int first[N],v[N],nxt[N];
int a[N],ans[N],val[N],root[N],size[N*40],lc[N*40],rc[N*40];
void add(int x,int y)
{
    t++;
    nxt[t]=first[x];
    first[x]=t;
    v[t]=y;
}
void build(int &root,int l,int r,int val)
{
    root=++tot;
    size[root]=1;
    if(l==r)  return;
    int mid=(l+r)>>1;
    if(val<=mid)  build(lc[root],l,mid,val);
    else  build(rc[root],mid+1,r,val);
}
int Merge(int x,int y)
{
    if(!x)  return y;
    if(!y)  return x;
    size[x]+=size[y];
    lc[x]=Merge(lc[x],lc[y]);
    rc[x]=Merge(rc[x],rc[y]);
    return x;
}
int calc(int root,int l,int r,int x,int y)
{
    if(l>=x&&r<=y)
      return size[root];
    int ans=0,mid=(l+r)>>1;
    if(x<=mid)  ans+=calc(lc[root],l,mid,x,y);
    if(y>mid)  ans+=calc(rc[root],mid+1,r,x,y);
    return ans;
}
void dfs(int x)
{
    int i,j;
    for(i=first[x];i;i=nxt[i])
    {
        j=v[i],dfs(j);
        root[x]=Merge(root[x],root[j]);
    }
    ans[x]=calc(root[x],1,m,val[x]+1,m);
}
int main()
{
    int x,i;
    scanf("%d",&n);
    for(i=1;i<=n;++i)  scanf("%d",&a[i]),val[i]=a[i];
    for(i=2;i<=n;++i)  scanf("%d",&x),add(x,i);
    sort(a+1,a+n+1),m=unique(a+1,a+n+1)-(a+1);
    for(i=1;i<=n;++i)
    {
        val[i]=lower_bound(a+1,a+m+1,val[i])-a;
        build(root[i],1,m,val[i]);
    }
    dfs(1);
    for(i=1;i<=n;++i)
      printf("%d\n",ans[i]);
    return 0;
}

 

线段树合并

标签:https   size   mes   turn   线段树   void   using   bzoj   val   

原文地址:https://www.cnblogs.com/downrainsun/p/11421359.html

(0)
(0)
   
举报
评论 一句话评论(0
登录后才能评论!
© 2014 mamicode.com 版权所有  联系我们:gaon5@hotmail.com
迷上了代码!