zoukankan      html  css  js  c++  java
  • Codeforces348B Apple Tree DFS

    题意:一颗苹果树上每个叶子结点苹果个数不同,现在需要从苹果树上取下最少的苹果,使得对于每一个结点,他的所有子树的苹果个数相同。

    两遍dfs。

    对于两颗子树,如果第一颗子树有四个结点,第二棵子树有五棵结点,又因为第一棵子树的权值等于第二棵子树的权值,所以说,两颗树的权值一定是  4 的倍数且是5的倍数,所以每棵子树都是20的倍数。深入理解一下这个意思,我们可以得到这样的结论,对于第一棵树,它转化为20个兄弟,并排着,第二棵树可以变成20个兄弟并排着,那么对于这两棵树的父亲可以变成40个结点并排。然后,来想一下,第一棵树的四个儿子,显然,每个儿子必然是5的倍数,所以每个儿子可以变成五份,这和第一个结点变成20份等价。

    现在解决这棵子树能分成多少份,下面就来解决,每个份 最大是多少,显然,对于每个叶子结点 L = min(L,叶子结点权值V / 叶子结点应该被分成NUM份)

     1 #include <iostream>
     2 #include <vector>
     3 #include <cstdio>
     4 #include <cstdlib>
     5 using namespace std;
     6 long long a[1111111];
     7 long long s[1111111];
     8 long long S;
     9 long long L = 1e15;
    10 long long ans = 0;
    11     int N;
    12 vector<int> E[1111111];
    13 long long gcd(long long x,long long y)
    14 {
    15     return y==0?x:gcd(y,x%y);
    16 }
    17 long long lca(long long x,long  long y)
    18 {
    19     return x*(y/gcd(x,y));
    20 }
    21 long long dfs(int u,int p)
    22 {
    23     if (E[u].size()==1&&u!=1)
    24     {
    25         s[u] = a[u];
    26         return 1LL;
    27     }
    28     long long num = 1;
    29     for (int i =0 ;i<E[u].size(); i++)
    30     {
    31         if (E[u][i]==p) continue;
    32         num = lca(num,dfs(E[u][i],u));
    33         s[u] += s[E[u][i]];
    34     }
    35     if ((E[u].size()-(u==1?0:1))*num >= S) {cout << S <<endl;exit(0);}
    36     return (E[u].size()-(u==1?0:1))*num;
    37 }
    38 void dfs2(int u,int p,long long num)
    39 {
    40     if (E[u].size()==1&&u!=1)
    41     {
    42         L = min(L,s[u]/num);
    43     }
    44     for (int i =0 ;i<E[u].size(); i++)
    45     {
    46         if (E[u][i]==p) continue;
    47         dfs2(E[u][i],u,num/(E[u].size()-(u==1?0:1)));
    48     }
    49 }
    50 int main()
    51 {
    52 
    53     //freopen("in.txt","r",stdin);
    54     cin >> N;
    55     for (int i = 1; i<=N; i++)
    56     {
    57          scanf("%I64d",&a[i]);
    58          S+=a[i];
    59     }
    60     for (int i = 1; i<N ; i++)
    61     {
    62         int x,y;
    63         scanf("%d%d",&x,&y);
    64         E[x].push_back(y);
    65         E[y].push_back(x);
    66     }
    67     long long dd = dfs(1,0);
    68     dfs2(1,0,dd);
    69     if (dd * L >= S)
    70     {
    71         cout <<0<<endl;
    72     }
    73     else
    74     {
    75         cout << S-dd*L<<endl;
    76     }
    77     return 0;
    78 }
    View Code
  • 相关阅读:
    zookeeper配置
    redis前端启动和后台启动的区别
    SpringMVC接受JSON参数详解及常见错误总结我改
    SpringMVC @RequestBody接收Json对象字符串
    spring MVC 如何接收前台传入的JSON对象数组
    springMVC 接收json字符串参数
    mysql数据库user表host字段的%问题
    mysql.user表中Host为%的含义
    开店攻略: 零售店铺经营的三大原则
    开店攻略: 如何巧妙接近顾客
  • 原文地址:https://www.cnblogs.com/HITLJR/p/6657514.html
Copyright © 2011-2022 走看看