zoukankan      html  css  js  c++  java
  • 树形DP Gym 100496H House of Representatives

    题目传送门

     1 /*
     2     题意:寻找一个根节点,求min f(u) = ∑ρ(v, u) * p(v)。ρ(v, u)是u到v的距离,p(v)是v点的权值
     3     树形DP:先从1出发遍历第一次,sum[u]计算u到所有子节点v的路径权值(之后的点路径有叠加,所以先把路径权值加后*w),
     4             计算f[u](缺少u节点以上的信息)。然后再遍历一遍,之前是DFS从下往上逆推,现在是顺推,把u节点以上的信息加上
     5     dp的部分不是很多,两个DFS函数想了很久,还是没完全理解:(
     6 */
     7 #include <cstdio>
     8 #include <cstring>
     9 #include <algorithm>
    10 #include <vector>
    11 using namespace std;
    12 
    13 typedef long long ll;
    14 const int MAXN = 1e5 + 10;
    15 const int INF = 0x3f3f3f3f;
    16 int p[MAXN];
    17 ll f[MAXN];
    18 ll sum[MAXN];
    19 vector<pair<int, int> > G[MAXN];
    20 
    21 void DFS1(int u, int rt)
    22 {
    23     f[u] = 0;    sum[u] = p[u];
    24     for (int i=0; i<G[u].size (); ++i)
    25     {
    26         int v = G[u][i].first;    int w = G[u][i].second;
    27         if (v == rt)    continue;
    28         DFS1 (v, u);
    29         f[u] += f[v] + sum[v] * w;    sum[u] += sum[v];
    30     }
    31 }
    32 
    33 void DFS2(int u, int rt)
    34 {
    35     for (int i=0; i<G[u].size (); ++i)
    36     {
    37         int v = G[u][i].first;    int w = G[u][i].second;
    38         if (v == rtGym 100496H House of Representatives)    continue;
    39         f[v] = f[u] - sum[v] * w + (sum[u] - sum[v]) * w;
    40         sum[v] = sum[u];
    41         DFS2 (v, u);
    42     }
    43 }
    44 
    45 int main(void)        //Gym 100496H House of Representatives
    46 {
    47 //    freopen ("H.in", "r", stdin);
    48     freopen ("house.in", "r", stdin);
    49     freopen ("house.out", "w", stdout);
    50 
    51     int n;
    52     while (scanf ("%d", &n) == 1)
    53     {
    54         for (int i=1; i<=n; ++i)    scanf ("%d", &p[i]);
    55         for (int i=1; i<=n; ++i)    G[i].clear ();
    56 
    57         for (int i=1; i<=n-1; ++i)
    58         {
    59             int u, v, w;    scanf ("%d%d%d", &u, &v, &w);
    60             G[u].push_back (make_pair (v, w));
    61             G[v].push_back (make_pair (u, w));
    62         }
    63 
    64         DFS1 (1, -1);    DFS2 (1, -1);
    65 
    66         int p = 1;
    67         for (int i=2; i<=n; ++i)
    68         {
    69             if (f[i] < f[p])    p = i;
    70         }
    71 
    72         printf ("%d %I64d
    ", p, f[p]);
    73     }
    74 
    75     return 0;
    76 }
    编译人生,运行世界!
  • 相关阅读:
    C# 全局热键
    Frida hook 初识
    xposed hook 复杂函数参数问题
    C# http post 中文乱码问题
    Fiddler 抓包https 问题
    C# HttpWebRequest 多线程超时问题
    Android Studio 无 Generate signed apk 菜单选项问题
    c#调用c++ dll const char* String类型转换问题。传值,与接收返回值问题
    C++中GB2312字符串和UTF-8之间的转换
    The underlying connection was closed: An unexpected error occurred on a send
  • 原文地址:https://www.cnblogs.com/Running-Time/p/4646054.html
Copyright © 2011-2022 走看看