• Linova and Kingdom


    题意:

    从一颗 (n) 个节点的树上,选择 (k) 个点,要求从这些点到根节点 (1) 的路径上经过的非选中的点的个数的总和最大。
    数据范围:(2≤n≤2⋅10^5, 1≤k<n)

    传送门

    分析:

      从深度和子树大小去考虑。
      首先,基于贪心的策略,优先选择深度大的点。对于一个点,如果选择该点,那么其子树中的所有点肯定均被选择了。考虑选择该点会最后的总和产生什么影响,首先会加上该点的深度,然后子树中所有点的贡献都会 (-1),即 (ans+=(depth[v]-sz[v]+1))。那么我们把该值排个序,取最大的 (k) 个就行了。

    反思:想到了点深度和子树大小,但没有把它们联系在一起考虑。

    代码:

    #include <bits/stdc++.h>
    #define pb push_back
    using namespace std;
    typedef long long ll;
    const int N=2e5+5;
    vector<int>G[N];
    int sz[N],a[N];
    bool cmp(int x,int y)
    {
        return x>y;
    }
    void dfs(int v,int p,int d)
    {
        sz[v]=1;
        for(int i=0;i<G[v].size();i++)
        {
            int u=G[v][i];
            if(u==p)
                continue;
            dfs(u,v,d+1);
            sz[v]+=sz[u];
        }
        a[v]=d-sz[v];
    }
    int main()
    {
        int n,k,v,u;
        ll ans=0;
        scanf("%d%d",&n,&k);
        for(int i=1;i<n;i++)
        {
            scanf("%d%d",&u,&v);
            G[u].pb(v);
            G[v].pb(u);
        }
        dfs(1,1,1);
        sort(a+1,a+1+n,cmp);
        for(int i=1;i<=k;i++)
            ans+=a[i];
        printf("%lld
    ",ans);
        return 0;
    }
    
  • 相关阅读:
    paper:Exploiting Query Reformulations for Web Search Result Diversification
    Z3
    IDA pro 类型参考
    Angr包含什么
    Gcc编译选项
    Angr
    一张图系列之PLT-GOT
    ELF头文件
    BROP_轮子
    Pwn_
  • 原文地址:https://www.cnblogs.com/1024-xzx/p/12728912.html
Copyright © 2020-2023  润新知