Count on a tree (a tree path of small K)

Topic links: https://www.spoj.com/problems/COT/en/

Meaning of the questions: first seek a tree A, B two points of a small number of paths K

Ideas: Chairman of the tree is actually a prefix and maintenance, while the prefix and do not have to appear on a linear table.

For example, we DFS from the root of a tree, from the root node to each node to obtain the dist [x] - This is a point on the root prefix -x distance and the root node path.

And use this prefix, we can solve some of the problems any path of trees, such as online inquiry [a, b] from the point - the answer is naturally dist [a] + dist [b] -2 * dist [lca (a , b)].

DFS traverse the whole tree, and then build a tree line on each node of a tree line of a "previous version" is located in the node's father node fa tree line.

Insertion point right (discrete sorted) using a method similar to the previous. So ask for [a, b], the answer is the root [a] + root [b] -root [lca (a, b)] - root [fa [lca (a, b)]] on the k-th largest.

#include<cstdio>
#include<cstring>
#include<queue>
#include<cmath>
#include<algorithm>
#include<map>
#include<vector>
#include<string>
#include<set>
#define ll long long
#define maxn 100007
using namespace std;
const int MAXN=1e5+100;
const int POW=18;
int num[MAXN],node[MAXN];
struct point
{
    int l;
    int r;
    int sum;
}T[MAXN*20];
int root[MAXN];
vector<int> G[MAXN];
int d[MAXN];
int p[MAXN][POW];
int tot;
int f[MAXN];
int n,m;
void build(int l,int r,int& rt)
{
    rt=++tot;
    T[rt].sum=0;
    if(l>=r)return;
    int m=(l+r)>>1;
    build(l,m,T[rt].l);
    build(m+1,r,T[rt].r);
}
void update(int last,int p,int l,int r,int &rt)
{
    rt=++tot;
    T[rt].l=T[last].l;
    T[rt].r=T[last].r;
    T[rt].sum=T[last].sum+1;
    if(l>=r)return ;
    int m=(l+r)>>1;
    if(p<=m)update(T[last].l,p,l,m,T[rt].l);
    else update(T[last].r,p,m+1,r,T[rt].r);
}
int query(int left_rt,int right_rt,int lca_rt,int lca_frt,int l,int r,int k)
{
    if(l>=r)return l;
    int m=(l+r)>>1;
    int cnt=T[T[right_rt].l].sum+T[T[left_rt].l].sum-T[T[lca_rt].l].sum-T[T[lca_frt].l].sum;
    if(k<=cnt)
        return query(T[left_rt].l,T[right_rt].l,T[lca_rt].l,T[lca_frt].l,l,m,k);
    else
        return query(T[left_rt].r,T[right_rt].r,T[lca_rt].r,T[lca_frt].r,m+1,r,k-cnt);
}
void dfs(int u,int fa,int cnt)
{
    f[u]=fa;
    d[u]=d[fa]+1;
    p[u][0]=fa;
    for(int i=1;i<POW;i++)
        p[u][i]=p[p[u][i-1]][i-1];
    update(root[fa],num[u],1,cnt,root[u]);
    for(int i=0;i<(int)G[u].size();i++)
    {
        int v=G[u][i];
        if(v==fa)continue;
        dfs(v,u,cnt);
    }
}
int lca(int a,int b)
{
    if(d[a]>d[b])
        a^=b,b^=a,a^=b;
    if(d[a]<d[b])
    {
        int del=d[b]-d[a];
        for(int i=0;i<POW;i++)
            if(del&(1<<i))b=p[b][i];
    }
    if(a!=b)
    {
        for(int i=POW-1;i>=0;i--)
        {
            if(p[a][i]!=p[b][i])
            {
                a=p[a][i],b=p[b][i];
            }
        }
        a=p[a][0],b=p[b][0];
    }
    return a;
}
void init()
{
    for(int i=0;i<=n;i++)
    {
        G[i].clear();
    }
    memset(d,0,sizeof(d));
    memset(p,0,sizeof(p));
    memset(f,0,sizeof(f));
}
int main()
{
    while(~scanf("%d%d",&n,&m))
    {
        init();
        for(int i=1;i<=n;i++)
        {
            scanf("%d",&num[i]);
            node[i]=num[i];
        }
        tot=0;
        sort(node+1,node+1+n);
        int cnt=unique(node+1,node+n+1)-node-1;
        for(int i=1;i<=n;i++)
        {
            num[i]=lower_bound(node+1,node+cnt+1,num[i])-node;
        }
        int a,b,c;
        for(int i=1;i<=n-1;i++)
        {
            scanf("%d%d",&a,&b);
            G[a].push_back(b);
            G[b].push_back(a);
        }
        build(1,cnt,root[0]);
        dfs(1,0,cnt );
        while(m--)
        {
            scanf("%d%d%d",&a,&b,&c);
            int t=lca(a,b);
            int id=query(root[a],root[b],root[t],root[f[t]],1,cnt,c);
            printf("%d\n",node[id]);
        }
    }
    return 0;
}

 

Guess you like

Origin www.cnblogs.com/2462478392Lee/p/11946592.html