zoukankan      html  css  js  c++  java
  • 2020牛客暑期多校训练营(第二场)

    C.Cover the Tree

    首先你从以一个度不为1的点作为根节点。然后你每次都连接一个叶子节点,这样显然是所有的边都可以被覆盖。即答案为度为1的点的个数,但是这样显然很大,可以优化,可以相当于把根节点当作中间节点,让叶子节点两两相连,显然答案已经出来了,就是(叶子+1)/2

    但是怎么两两配对是一个问题,下图提供了证明:

    #include <iostream>
    #include <cstdio>
    #include <cstring>
    #include <algorithm>
    using namespace std;
    const int maxn=2e5+7;
    int n, m, t, ans[maxn];
    int cnt, head[maxn];
    int deg[maxn], root;
    struct node{
        int nxt,to;
    }e[maxn<<1];
    void add(int u,int v){
         e[cnt].nxt=head[u];
         e[cnt].to=v;
         head[u]=cnt++;
    }
    void dfs(int u, int pre){
        if(deg[u]==1) ans[++t] = u;
        for(int i = head[u]; i != -1; i = e[i].nxt){
            int to = e[i].to;
            if(to != pre) dfs(to, u);
        }
    }
    
    int main (){
        scanf("%d", &n);
        memset(head,-1,sizeof(head));
        for(int i = 1; i <= n-1; i++){
            int u, v;
            scanf("%d%d", &u, &v);
            add(u,v), add(v,u);
            deg[u]++, deg[v]++;
        }
        for(int i = 1; i <= n; i++){
            if(deg[i]>1){
              root = i;
              break;
            }
        }
        dfs(root, -1);
        if(t%2==1) ans[++t] = root;
        printf ("%d
    ", t/2);
        for(int i = 1; i <= t/2; i++){
            printf ("%d %d
    ", ans[i], ans[t/2+i]);
        }
    }
    View Code
  • 相关阅读:
    Linux 网络编程之ioctl函数
    驱动编写及编译例子
    字符串字面量与指针
    ubuntu 下安装nfs
    android 开源项目
    【转】中间件的历史来看移动App开发的未来
    android 关联源码
    【转】android 蓝牙
    【转】Android Google Map API使用的八个步骤
    【转】Android 国内集成使用谷歌地图
  • 原文地址:https://www.cnblogs.com/wizarderror/p/13302932.html
Copyright © 2011-2022 走看看