• CF613D


    这是个假题吧...

    首先显然上虚树了

    然后我们考虑一下最优策略:

    如果虚树两节点都是关键点,那么这两点之间至少选一个

    如果一个节点本身是关键点,那么我们必须覆盖下下面所有点

    如果一个节点本身不是关键点,那么这个点可选可不选,这一点要基于下面有多少个上来来决定

    也就是说,我们在虚树上dfs的过程中需要考虑到每个子节点向上会传递多少个节点,也就是说每个节点选最少的情况下可能不能完全封死下面的点,可能会向上传递一些节点,这时我们就需要处理这个问题

    但是向上传递一部分节点一定是更优的,因为我们这时只需选一个LCA即可堵住多个节点

    因此我们直接讨论:如果当前点不是关键点而底下传上来的点数>1,那么这个点就需要选

    如果这个点本身就是关键点,那么就要封上所有底下传上来的点,然后向上传一个点即可

    贴代码:

    #include <cstdio>
    #include <cmath>
    #include <cstring>
    #include <cstdlib>
    #include <iostream>
    #include <algorithm>
    #include <queue>
    #include <stack>
    #include <vector>
    #include <map>
    using namespace std;
    struct Edge
    {
        int nxt;
        int to;
    }edge[200005];
    int head[100005];
    int f[100005][25];
    int inr[100005],our[100005],dep[100005];
    int my_stack[100005],mine_stack[100005];
    bool bas[100005],vis[100005];
    int dp[100005];
    vector <int> v[100005];
    map <int,int> acc[100005];
    int deep=0;
    int cnt=1;
    int n,q,m;
    void add(int l,int r)
    {
        edge[cnt].nxt=head[l];
        edge[cnt].to=r;
        acc[l][r]=1;
        head[l]=cnt++;
    }
    void dfs(int x,int fx)
    {
        f[x][0]=fx,inr[x]=++deep,dep[x]=dep[fx]+1;
        for(int i=1;i<=20;i++)f[x][i]=f[f[x][i-1]][i-1];
        for(int i=head[x];i;i=edge[i].nxt)
        {
            int to=edge[i].to;
            if(to==fx)continue;
            dfs(to,x);
        }
        our[x]=++deep;
    }
    bool cmp(int x,int y)
    {
        return inr[x]<inr[y];
    }
    int LCA(int x,int y)
    {
        if(dep[x]>dep[y])swap(x,y);
        for(int i=20;i>=0;i--)if(dep[f[y][i]]>=dep[x])y=f[y][i];
        if(x==y)return x;
        int ret;
        for(int i=20;i>=0;i--)
        {
            if(f[x][i]!=f[y][i])x=f[x][i],y=f[y][i];
            else ret=f[x][i];
        }
        return ret;
    }
    bool be_in(int x,int y)//y in x
    {
        return inr[y]>inr[x]&&our[y]<our[x];
    }
    int redfs(int x)
    {
        int temp=0;
        for(int i=0;i<v[x].size();i++)
        {
            int to=v[x][i];
            if(bas[x]&&bas[to]&&acc[x][to])return -1;
            int t=redfs(to);
            if(t==-1)return -1;
            temp+=t;
            dp[x]+=dp[to];
        }
        if(!bas[x]){if(temp>1)temp=0,dp[x]++;}
        else dp[x]+=temp,temp=1;
        return temp;
    }
    inline int read()
    {
        int f=1,x=0;char ch=getchar();
        while(ch<'0'||ch>'9'){if(ch=='-')f=-1;ch=getchar();}
        while(ch>='0'&&ch<='9'){x=x*10+ch-'0';ch=getchar();}
        return x*f;
    }
    int main()
    {
        n=read();
        for(int i=1;i<n;i++)
        {
            int x=read(),y=read();
            add(x,y),add(y,x);
        }
        dfs(1,1);
        q=read();
        while(q--)
        {
            m=read();
            for(int i=1;i<=m;i++)my_stack[i]=read(),bas[my_stack[i]]=vis[my_stack[i]]=1;
            sort(my_stack+1,my_stack+m+1,cmp);
            int t=m;
            for(int i=1;i<m;i++)
            {
                int fa=LCA(my_stack[i],my_stack[i+1]);
                if(!vis[fa])vis[fa]=1,my_stack[++t]=fa;
            }
            sort(my_stack+1,my_stack+t+1,cmp);
            int T1=0,rt;
            for(int i=1;i<=t;i++)
            {
                while(T1&&!be_in(mine_stack[T1],my_stack[i]))T1--;
                if(!T1)rt=my_stack[i];
                else v[mine_stack[T1]].push_back(my_stack[i]);
                mine_stack[++T1]=my_stack[i];
            }
            int tmp=redfs(rt);
            if(tmp==-1)printf("-1
    ");
            else printf("%d
    ",dp[rt]);
            for(int i=1;i<=t;i++)v[my_stack[i]].clear(),dp[my_stack[i]]=bas[my_stack[i]]=vis[my_stack[i]]=0;
        }
        return 0;
    }
  • 相关阅读:
    oracle的安装与plsql的环境配置
    Working with MSDTC
    soapui-java.lang.Exception Failed to load url
    Oracle 一个owner访问另一个owner的table,不加owner
    Call API relation to TLS 1.2
    Call API HTTP header Authorization: Basic
    VS2008 .csproj cannot be opened.The project type is not supported by this installat
    The changes couldn't be completed.Please reboot your computer and try again.
    Create DB Table View Procedure
    DB Change
  • 原文地址:https://www.cnblogs.com/zhangleo/p/11147930.html
Copyright © 2020-2023  润新知