题目链接:http://www.lydsy.com:808/JudgeOnline/problem.php?id=3572

题意:给出一棵树。若干询问。每个询问给出m个点,输出每个点管辖的点的个数。x被y管辖(y在给出的m个点中)是说不存在其他的m个点中的点yy,使得pair<dis(x,yy),yy>   <  pair<dis(x,y),y>。

思路:建立虚树。

const int INF=100000005;
const int N=333333;

vector<int> gg[N];
int f[N][20];
int dep[N];
int n,m;

int id;
int dfn[N];
int size[N];

void DFS(int u,int pre,int d)
{
    dep[u]=d;
    f[u][0]=pre;
    dfn[u]=++id;
    size[u]=1;
    int i;
    for(i=0;i<SZ(gg[u]);i++)
    {
        int v=gg[u][i];
        if(v!=pre) DFS(v,u,d+1),size[u]+=size[v];
    }
}

int getLca(int u,int v)
{
    if(dep[u]<dep[v]) swap(u,v);
    int x=dep[u]-dep[v];
    int i;
    for(i=0;i<20;i++) if(x&(1<<i)) u=f[u][i];
    if(u==v) return u;
    for(i=19;i>=0;i--) if(f[u][i]&&f[v][i]&&f[u][i]!=f[v][i])
    {
        u=f[u][i];
        v=f[v][i];
    }
    return f[u][0];
}

int get(int u,int d)
{
    int i;
    for(i=19;i>=0;i--) if(dep[f[u][i]]>=d) u=f[u][i];
    return u;
}

pair<int,int> g[N];
int tot,a[N],b[N];

int ans[N];

int st[N];

int cmp(int x,int y)
{
    return dfn[x]<dfn[y];
}

int fa[N];

void init()
{
    sort(a+1,a+m+1,cmp);
    int top=0;
    int i;
    for(i=1;i<=m;i++)
    {
        int u=a[i];
        if(!top) fa[st[++top]=u]=0;
        else
        {
            int lca=getLca(st[top],u);
            while(dep[st[top]]>dep[lca])
            {
                if(dep[st[top-1]]<=dep[lca]) fa[st[top]]=lca;
                top--;
            }
            if(st[top]!=lca)
            {
                a[++tot]=lca;
                g[lca]=MP(INF,0);
                fa[lca]=st[top];
                st[++top]=lca;
            }
            fa[u]=lca;
            st[++top]=u;
        }
    }
}

int dis[N];
int tmp[N];

void cal()
{
    sort(a+1,a+tot+1,cmp);
    int i;
    for(i=1;i<=tot;i++)
    {
        int u=a[i];
        tmp[u]=size[u];
        if(i>1) dis[u]=dep[u]-dep[fa[u]];
    }
    for(i=tot;i>1;i--)
    {
        int u=a[i],pre=fa[u];
        g[pre]=min(g[pre],MP(g[u].first+dis[u],g[u].second));
    }

    for(i=2;i<=tot;i++)
    {
        int u=a[i],pre=fa[u];
        g[u]=min(g[u],MP(g[pre].first+dis[u],g[pre].second));
    }

    for(i=1;i<=tot;i++)
    {
        int u=a[i],pre=fa[u];
        if(i==1) ans[g[u].second]+=n-size[u];
        else
        {
            int x=get(u,dep[pre]+1);
            int sum=size[x]-size[u];
            tmp[pre]-=size[x];
            if(g[pre].second==g[u].second) ans[g[u].second]+=sum;
            else
            {
                int xx=g[pre].first+g[u].first+dis[u];
                int M=dep[u]-(xx/2-g[u].first);
                if(xx%2==0&&g[u].second>g[pre].second) M++;
                int y=size[get(u,M)]-size[u];
                ans[g[u].second]+=y;
                ans[g[pre].second]+=sum-y;
            }
        }
    }
    for(i=1;i<=tot;i++) ans[g[a[i]].second]+=tmp[a[i]];
}

int main()
{

    scanf("%d",&n);
    int i;
    for(i=1;i<n;i++)
    {
        int x,y;
        scanf("%d%d",&x,&y);
        gg[x].pb(y);
        gg[y].pb(x);
    }
    DFS(1,0,1);
    int j;
    for(i=1;(1<<i)<=n;i++) for(j=1;j<=n;j++) f[j][i]=f[f[j][i-1]][i-1];
    int Q;
    scanf("%d",&Q);
    while(Q--)
    {
        scanf("%d",&m);
        for(i=1;i<=m;i++)
        {
            a[i]=b[i]=getInt();
            g[a[i]]=MP(0,a[i]);
            ans[a[i]]=0;
        }
        tot=m;
        init();
        cal();
        for(i=1;i<=m;i++)
        {
            printf("%d ",ans[b[i]]);
        }
        puts("");
    }
}

BZOJ 3752 世界树的更多相关文章

  1. BZOJ 3572 世界树

    Description 世界树是一棵无比巨大的树,它伸出的枝干构成了整个世界.在这里,生存着各种各样的种族和生灵,他们共同信奉着绝对公正公平的女神艾莉森,在他们的信条里,公平是使世界树能够生生不息.持 ...

  2. bzoj 3752: Hack 预处理+暴力dfs

    题目大意: 定义字符串的hash值\(h = \sum_{i=0}^{n-1}p^{n-i-1}s_i\) 现在给定K个长度不超过L的字符串S,对于每个字符串S,求字典序最小长度不超过L的字符串T使得 ...

  3. BZOJ 3572 世界树(虚树)

    http://www.lydsy.com/JudgeOnline/problem.php?id=3572 思路:建立虚树,然后可以发现,每条边不是同归属于一端,那就是切开,一半给上面,一半给下面. # ...

  4. bzoj 3572世界树 虚树+dp

    题目大意: 给一棵树,每次给出一些关键点,对于树上每个点,被离它最近的关键点(距离相同被标号最小的)控制 求每个关键点控制多少个点 分析: 虚树+dp dp过程如下: 第一次dp,递归求出每个点子树中 ...

  5. BZOJ 2648 世界树

    题目传送门 分析: 喜 闻 乐 见 的虚树 但是建好虚树后的DP也非常的恶心 我们先考虑每个关键点的归哪个点管 先DFS一次计算儿子节点归属父亲 再DFS一次计算父亲节点归属儿子 然后然后我们对于虚树 ...

  6. BZOJ 3572: [Hnoi2014]世界树

    BZOJ 3572: [Hnoi2014]世界树 标签(空格分隔): OI-BZOJ OI-虚数 OI-树形dp OI-倍增 Time Limit: 20 Sec Memory Limit: 512 ...

  7. bzoj 3572: [Hnoi2014]世界树 虚树 && AC500

    3572: [Hnoi2014]世界树 Time Limit: 20 Sec  Memory Limit: 512 MBSubmit: 520  Solved: 300[Submit][Status] ...

  8. bzoj 3572 [Hnoi2014]世界树(虚树+DP)

    3572: [Hnoi2014]世界树 Time Limit: 20 Sec  Memory Limit: 512 MBSubmit: 645  Solved: 362[Submit][Status] ...

  9. BZOJ 3572 【HNOI2014】 世界树

    题目链接:世界树 首先看到\(\sum m_i\le 3\times 10^5\)这个条件,显然这道题就需要用虚树了. 在我们构建出虚树之后,就可以用两遍\(dfs\)来求出离每个点最近的议事处了.然 ...

随机推荐

  1. Android2.2快速入门 zz

    http://www.cnblogs.com/over140/archive/2010/09/27/1836567.html 前言 这是前段时间用于公司Android入门培训的资料,学习Android ...

  2. PAT乙级 1011. A+B和C (15)

    1011. A+B和C (15) 时间限制 100 ms 内存限制 65536 kB 代码长度限制 8000 B 判题程序 Standard 作者 HOU, Qiming 给定区间[-231, 231 ...

  3. Java笔试题解答和部分面试题

    面试类  银行类的问题 问题一:在多线程环境中使用HashMap会有什么问题?在什么情况下使用get()方法会产生无限循环? HashMap本身没有什么问题,有没有问题取决于你是如何使用它的.比如,你 ...

  4. Linux字符设备驱动结构(一)--cdev结构体、设备号相关知识机械【转】

    本文转载自:http://blog.csdn.net/zqixiao_09/article/details/50839042 一.字符设备基础知识 1.设备驱动分类 linux系统将设备分为3类:字符 ...

  5. jquery选择器中两个class是什么意思?

    jquery选择器中两个class是什么意思? $(".class1 .class2") 选择class1元素下class2的元素(中间有空格)$(".class1.cl ...

  6. Java排序算法(1)

    Java中的排序算法(1)  package com.softeem.jbs.lesson4; import java.util.Random; /** * 排序测试类 * * 排序算法的分类如下: ...

  7. mysql使用索引扫描来做排序

    mysql有两种方式可以生成有序的结果,通过排序操作或者按照索引顺序扫描,如果explain的type列的值为index,则说明mysql使用了索引扫描来做排序(不要和extra列的Using ind ...

  8. List与Set的contains方法效率问题

    今天看到网上一篇文章说:Set检索元素效率低下,删除和插入效率高:List查找元素效率高,插入删除元素效率低.于是想到List虽然用get(index)方法查询效率高,但是若用contains方法查询 ...

  9. Java四种线程池newCachedThreadPool,newFixedThreadPool,newScheduledThreadPool,newSingleThreadExecutor

    1.new Thread的弊端 执行一个异步任务你还只是如下new Thread吗? Java new Thread(new Runnable() { @Override public void ru ...

  10. python: html

    1. 三把利剑(html css js) css(颜色 位置) js (动) 2. 标签的分类:块级标签和行内标签 块级标签(div h p) 行内标签(span) 3. 标签存在的意义:为了方便操作 ...