zoukankan      html  css  js  c++  java
  • spoj+B

    题目链接:COT - Count on a tree

    题解:跟数组求第K大差不多,这个要求下求下lca,然后区间查询的应该是sum[u]+sum[v]-sum[lca(u,v)]-sum[f[lac(u,v)][0]];

    You are given a tree with N nodes. The tree nodes are numbered from 1 to N. Each node has an integer weight.

    We will ask you to perform the following operation:

    • u v k : ask for the kth minimum weight on the path from node u to node v

    Input

    In the first line there are two integers N and M. (N, M <= 100000)

    In the second line there are N integers. The ith integer denotes the weight of the ith node.

    In the next N-1 lines, each line contains two integers u v, which describes an edge (u, v).

    In the next M lines, each line contains three integers u v k, which means an operation asking for the kth minimum weight on the path from node u to node v.

    Output

    For each operation, print its result.

    Example

    Input:
    8 5
    105 2 9 3 8 5 7 7
    1 2
    1 3
    1 4
    3 5
    3 6
    3 7
    4 8
    2 5 1
    2 5 2
    2 5 3
    2 5 4
    7 8 2 
    Output:
    2
    8
    9
    105
    #include<bits/stdc++.h>
    #include<set>
    #include<cstdio>
    #include<iomanip>
    #include<iostream>
    #include<string>
    #include<cstring>
    #include<algorithm>
    #define pb push_back
    #define ll long long
    #define PI 3.14159265
    //#define ls l,m,rt<<1
    //#define rs m+1,r,rt<<1|1
    #define eps 1e-7
    typedef unsigned long long ull;
    const int mod=1e9+9;
    const ll inf=0x3f3f3f3f3f3f3f;
    const int maxn=1e5+5;
    using namespace std;
    int a[maxn],b[maxn],head[maxn],sum[maxn*30],rt[maxn],dep[maxn],f[maxn][20],n,m,tol,sz;
    int ls[maxn*30],rs[maxn*30],tot;
    struct edge
    {
        int to,next;
    }eg[maxn*4];
    void add_edge(int u,int v)
    {
        eg[tol].to=v;
        eg[tol].next=head[u];
        head[u]=tol++;
    }
    void dfs(int v,int d,int p)
    {
        f[v][0]=p;
        dep[v]=d;
        for(int i=head[v];i!=-1;i=eg[i].next)
        {
            if(eg[i].to!=p)dfs(eg[i].to,d+1,v);
        }
    }
    void init(int c)
    {
        dfs(1,0,0);
        for(int k=0;k<19;k++)
        {
            for(int i=1;i<=c;i++)
            {
                if(f[i][k]==0)f[i][k+1]=0;
                else f[i][k+1]=f[f[i][k]][k];
            }
        }
    }
    void update(int &o,int pre,int l,int r,int x)
    {
    
        o=++tot;
        ls[o]=ls[pre];
        rs[o]=rs[pre];
        sum[o]=sum[pre]+1;
        int m=(l+r)>>1;
        if(l==r)return ;
        if(x<=m)update(ls[o],ls[pre],l,m,x);
        else update(rs[o],rs[pre],m+1,r,x);
    }
    void dfs1(int v,int p)
    {
        update(rt[v],rt[p],1,sz,a[v]);
        for(int i=head[v];i!=-1;i=eg[i].next)
        {
            if(eg[i].to!=p)dfs1(eg[i].to,v);
        }
    }
    int lca(int u,int v)
    {
        if(dep[u]>dep[v])swap(u,v);
        for(int i=0;i<20;i++)
        {
            if(dep[v]-dep[u]>>i&1)v=f[v][i];
        }
        if(v==u)return v;
        for(int i=19;i>=0;i--)
        {
            if(f[v][i]!=f[u][i])
            {
                u=f[u][i];
                v=f[v][i];
            }
        }
        return f[v][0];
    }
    void build(int &o,int l,int r)
    {
        o=++tot;
        sum[o]=0;
        if(l==r)return;
        int m=(l+r)>>1;
        build(ls[o],l,m);
        build(rs[o],m+1,r);
    }
    int query(int l,int r,int k,int pu,int pv,int pl,int pfl)
    {
        if(l==r)return l;
        int m=(l+r)>>1;
        int cnt=sum[ls[pu]]+sum[ls[pv]]-sum[ls[pl]]-sum[ls[pfl]];
        if(cnt>=k)return query(l,m,k,ls[pu],ls[pv],ls[pl],ls[pfl]);
        else return query(m+1,r,k-cnt,rs[pu],rs[pv],rs[pl],rs[pfl]);
    }
    int main()
    {
        while(~scanf("%d %d",&n,&m))
        {
            memset(head,-1,sizeof(head));tot=0;tol=0;
            for(int i=1;i<=n;i++)
            {
                scanf("%d",&a[i]);b[i]=a[i];
            }
            sort(b+1,b+n+1);
             sz=unique(b+1,b+1+n)-b-1;
            for(int i=1;i<=n;i++)
            {
                 a[i]=lower_bound(b+1,b+1+sz,a[i])-b;
            }
            for(int i=0;i<n-1;i++)
            {
                int u,v;
                scanf("%d %d",&u,&v);
                add_edge(u,v);
                add_edge(v,u);
            }
            init(n);
            build(rt[0],1,sz);
            dfs1(1,0);
            while(m--)
            {
                int u,v,k;
                scanf("%d %d %d",&u,&v,&k);
                int lc=lca(v,u);
              //  cout<<lc<<"*"<<endl;
                int id=query(1,sz,k,rt[u],rt[v],rt[lc],rt[f[lc][0]]);
                printf("%d
    ",b[id]);
            }
        }
        return 0;
    }
     
  • 相关阅读:
    [React] {svg, css module, sass} support in Create React App 2.0
    [NPM] npm check to update the dependencies
    [RxJS] `add` Inner Subscriptions to Outer Subscribers to `unsubscribe` in RxJS
    [RxJS] Implement RxJS `concatMap` by Waiting for Inner Subscriptions to Complete
    [React] PureComponent in React
    [RxJS] Implement RxJS `switchMap` by Canceling Inner Subscriptions as Values are Passed Through
    [RxJS] Implement RxJS `mergeMap` through inner Observables to Subscribe and Pass Values Through
    [RxJS] Chain RxJS Operators Together with a Custom `pipe` Function using Array.reduce
    [RxJS] Implement the `map` Operator from Scratch in RxJS
    [RxJS] Create a Reusable Operator from Scratch in RxJS
  • 原文地址:https://www.cnblogs.com/lhclqslove/p/8679080.html
Copyright © 2011-2022 走看看