zoukankan      html  css  js  c++  java
  • POJ 1655 Balancing Act (树状dp入门)

    Description

    Consider a tree T with N (1 <= N <= 20,000) nodes numbered 1...N. Deleting any node from the tree yields a forest: a collection of one or more trees. Define the balance of a node to be the size of the largest tree in the forest T created by deleting that node from T.
    For example, consider the tree:

    Deleting node 4 yields two trees whose member nodes are {5} and {1,2,3,6,7}. The larger of these two trees has five nodes, thus the balance of node 4 is five. Deleting node 1 yields a forest of three trees of equal size: {2,6}, {3,7}, and {4,5}. Each of these trees has two nodes, so the balance of node 1 is two.

    For each input tree, calculate the node that has the minimum balance. If multiple nodes have equal balance, output the one with the lowest number.

    Input

    The first line of input contains a single integer t (1 <= t <= 20), the number of test cases. The first line of each test case contains an integer N (1 <= N <= 20,000), the number of congruence. The next N-1 lines each contains two space-separated node numbers that are the endpoints of an edge in the tree. No edge will be listed twice, and all edges will be listed.

    Output

    For each test case, print a line containing two integers, the number of the node with minimum balance and the balance of that node.

    Sample Input

    1
    7
    2 6
    1 2
    1 4
    4 5
    3 7
    3 1
    

    Sample Output

    1 2

    就是给你一棵树,让你在树上去掉一个节点,这样就形成了许多子树,设所有子树中点个数最多的那颗子树的点的个数为x,现在让这个x最小,问你应该剪掉哪个节点,x是多少?
    根据树形结构的特殊性,从树根走到叶子节点是严格按照层次顺序的。我现在就开始做dp。首先我们先定义一个dp数组。
    我们还需要一个num[x]数组,用来表示以x为树根的子树上有多少节点

    对于每一个节点,去掉它所得到的x的值是什么呢?1.它所有子节点为根的子树的最大值 2.除了x和它下面所有的子树,剩下全部的节点。这两者比较最大值就可以了。

    刚刚看了白书,就是让找树的重心。
    代码如下:
     1 #include <cstdio>
     2 #include <cstring>
     3 #include <cmath>
     4 #include <algorithm>
     5 using namespace std;
     6 #define M 20020
     7 int n;
     8 struct Node
     9 {
    10     int to,pre;
    11 }edge[M*2];
    12 int head[M],tot,dp[M],num[M];
    13 void init ()
    14 {
    15     memset(head,-1,sizeof head);
    16     tot=0;
    17 }
    18 void addedge (int u,int v)
    19 {
    20     edge[tot].to=v;
    21     edge[tot].pre=head[u];
    22     head[u]=tot++;
    23 }
    24 void dfs (int u,int prenode)
    25 {
    26     dp[u]=0;
    27     num[u]=1;
    28     for (int i=head[u];i!=-1;i=edge[i].pre)
    29     {
    30         int v=edge[i].to;
    31         if (v==prenode)
    32         continue;
    33         dfs(v,u);
    34         dp[u]=max(dp[u],num[v]);
    35         num[u]+=num[v];
    36     }
    37     dp[u]=max(dp[u],n-num[u]);
    38 }
    39 int main()
    40 {
    41     int t;
    42     scanf("%d",&t);
    43     while (t--)
    44     {
    45         scanf("%d",&n);
    46         init();
    47         for (int i=1;i<n;++i)
    48         {
    49             int u,v;
    50             scanf("%d %d",&u,&v);
    51             addedge(u,v);
    52             addedge(v,u);
    53         }
    54         dfs(1,-1);
    55         int ans1=1,ans2=dp[1];
    56         for (int i=2;i<=n;++i)
    57         {
    58             if (ans2>dp[i])
    59             {
    60                 ans1=i;
    61                 ans2=dp[i];
    62             }
    63         }
    64         printf("%d %d
    ",ans1,ans2);
    65     }
    66     return 0;
    67 }
  • 相关阅读:
    类型约束的本质:泛型是不完备类型,只有合乎要求的构造才能正确使用和访问。
    函数的泛型约束是函数签名的一部分,不符合约束的初始调用将不能查找到函数(报错)
    泛型约束-swift
    swift语言的特点(相对于oc)
    extension Kingfisher where Base: Image:泛型类型的具体化与实例化
    “标准查询运算符”是组成语言集成查询 (LINQ) 模式的方法
    int 和bigint差别有多大?
    MySql5.7 配置文件 my.cnf 设置
    关于mysql 出现 1264 Out of range value for column 错误的解决办法
    git中Please enter a commit message to explain why this merge is necessary.
  • 原文地址:https://www.cnblogs.com/agenthtb/p/5948396.html
Copyright © 2011-2022 走看看