• Tree HDU6228


    题目链接
    Problem Description
    Consider a un-rooted tree T which is not the biological significance of tree or plant, but a tree as an undirected graph in graph theory with n nodes, labelled from 1 to n. If you cannot understand the concept of a tree here, please omit this problem.
    Now we decide to colour its nodes with k distinct colours, labelled from 1 to k. Then for each colour i = 1, 2, · · · , k, define Ei as the minimum subset of edges connecting all nodes coloured by i. If there is no node of the tree coloured by a specified colour i, Ei will be empty.
    Try to decide a colour scheme to maximize the size of E1 ∩ E2 · · · ∩ Ek, and output its size.
    Input
    The first line of input contains an integer T (1 ≤ T ≤ 1000), indicating the total number of test cases.
    For each case, the first line contains two positive integers n which is the size of the tree and k (k ≤ 500) which is the number of colours. Each of the following n - 1 lines contains two integers x and y describing an edge between them. We are sure that the given graph is a tree.
    The summation of n in input is smaller than or equal to 200000.
    Output
    For each test case, output the maximum size of E1 ∩ E1 ... ∩ Ek.
    SampleInput
    3
    4 2
    1 2
    2 3
    3 4
    4 2
    1 2
    1 3
    1 4
    6 3
    1 2
    2 3
    3 4
    3 5
    6 2
    SampleOutput
    1
    0
    1

    【思路】:我们可以得知,答案肯定在树的直径上,那么我们要考虑在树的直径上的两点能否满足题目要求的条件
    其实容易得知,满足条件即,子树的点数>=k 所有的点数-子树的点数>=k那么就可以知道,相连的这条边是满足条
    件的,将答案加1即可,然后输出答案
    因为是无根树,所以我们先找到一个树直径上的端点,再从端点开始处理出子树大小,再从端点开始搜索可以得到答案
    

    附上代码:

    #include <bits/stdc++.h>
    using namespace std;
    const int MAXN = 200005;
    struct EDGE{
        int u, v, next;
    }arr[MAXN << 1];
    int head[MAXN];
    int tot = 0, re;
    int n, k;
    void Init(){
        tot = 0;
        memset(head, -1, sizeof(head));
    }
    void add(int u, int v){
        arr[tot].u = u, arr[tot].v = v, arr[tot].next = head[u], head[u] = tot ++;
    }
    int vids[MAXN], maxs, result;
    void dfs1(int u, int step){
        if(step > maxs){
            result = u;
        }
        vids[u] = 1;
        for(int i = head[u]; ~i; i = arr[i].next){
            int v = arr[i].v;
            if(!vids[v]){
                vids[v] = 1;
                dfs1(v, step + 1);
                vids[v] = 0;
            }
        }
        return ;
    }
    int size[MAXN];
    void solve_son_size(int u){
        vids[u] = 1, size[u] = 1;
        for(int i = head[u]; ~i; i = arr[i].next){
            int v = arr[i].v;
            if(!vids[v]){
                solve_son_size(v);
                size[u] += size[v];
            }
        }
        return;
    }
    void solve(int u){
        vids[u] = 1;
        if(n - size[u] >= k && size[u] >= k){
            re ++;
        }
        for(int i = head[u]; ~i; i = arr[i].next){
            int v = arr[i].v;
            if(!vids[v]){
                solve(v);
            }
        }
    }
    int main(){
        int T;
        scanf("%d", &T);
        while(T --){
            scanf("%d%d", &n, &k);
            Init();
            for(int i = 0; i < n - 1; i ++){
                int u, v;
                scanf("%d%d", &u, &v);
                add(u, v);
                add(v, u);
            }
            maxs = 0;
            memset(vids, 0, sizeof(vids));
            dfs1(1, 0);
            //result 树的新根
            //通过树的新根,求点的子树大小
            //然后从根开始走,判断如果子树与上面的树都大于k那么答案++
            memset(vids, 0, sizeof(vids));
            memset(size, 0, sizeof(size));
            solve_son_size(result);
            re = 0;
            memset(vids, 0, sizeof(vids));
            solve(result);
            printf("%d
    ", re);
        }
        return 0;
    }
    
  • 相关阅读:
    Eclipse乱码怎么办
    GitHub 优秀Android 开源项目
    Android开发技术周报
    GitHub上最火的40个iOS开源项目
    GitHub上最火的74个Android开源项目
    2015年十大热门Android开源新项目
    dotfuscator初步
    Top 10 steps to optimize data access in SQL Server
    How I explained Design Patterns to my wife
    .NET_Framework_version_history
  • 原文地址:https://www.cnblogs.com/qq136155330/p/11817018.html
Copyright © 2020-2023  润新知