思路:

  只能刷部分节点数m,总节点数n。如果m>=n那么就可以全刷了,那就不用任何算法了。如果m<n那么就要有取舍了。用DP思路,记录下每个节点如果获得到1~m个选择所能获得的最大权值。这里的树不仅仅是二叉,可能是多叉。所以一个节点怎么合理分配给每个孩子的空间大小很关键,当第一个孩子获得了1空间,那么后面的孩子所能获得的空间就要少一个了。这样穷举每个孩子能得到的空间,来求当前节点的最大权值,会有很多种可能,m!。不用这么做。

递归步骤:

  假设状态记录为 dp[节点][该节点所获得的空间大小]    注:该节点所获得的空间大小可能从1~m,m指该节点在树的第几层。

(1)如果当前节点最多只能获得1的空间,那么就不用计算大于1的可能了,仅需计算他自己,也就是dp[自己][1]。这个节点就是根节点的广度搜索的第m层(m是根节点所能获得的空间大小)。

(2)对于当前节点node,所能获得的最大空间m,那么需要先计算出所有孩子的数据先,不然怎么计算node的最大权值。要知道,node的最大权值都是靠其孩子来支撑的。所以这一步先将m减1,然后m-1全部给孩子,孩子就能计算出从1~m-1的可能了。

(3)要更新当前节点node自己的所有数据了,也就是dp[node][1~m]。考虑到穷举会有m!种可能。得找另外的办法解决:考虑到当前节点的所有数据全靠孩子,那么对所有孩子逐个考虑,假设孩子为i。接着要考虑更新node的第j个数据,j=m...1,就是从大到小来更新(有点像01背包),必须从大到小,因为每当我们更新第j个数据dp[node][j]时,需要用到前面dp[node][<j]的值,假如从小到大,那么当考虑到dp[node][j]时,前面dp[node][<j]中已经包含了第i个孩子的数据了,这样就造成了重复,比如dp[node][2]=10,这里面取第1个孩子和node节点,接着dp[node][4]=max(dp[node][4], dp[node][4-2]+dp[第1个孩子][2])= max(dp[node][4], dp[node][2]+dp[第1个孩子][2])  表示给第一个1孩子2个空间所能获得大小,而dp[node][2]已经取了第1个孩子,dp[第1个孩子][2]又取该孩子一次,那么node的第1个孩子就被收藏了两次。重复了。正确的循环如下代码

 #include <iostream>
#include <cstring>
#include <vector>
#include <stdio.h>
using namespace std; const int N2=; //平方
const int N3=; //立方
int value[N3]; //权值
vector< vector<int> > edge(N2); //边
int dp[N2][N3]; //dp值 int tree_dp( int node ,int m )
{
if(m==) //如果分给node为1个空间,那只能收获他自己而已
{
dp[node][m]=value[node];
return ;
} //递归计算出所有孩子
for(int i=; i<edge[node].size(); i++) //对于每个孩子
tree_dp(edge[node][i], m- ); //更新本节点的所有可能性
dp[node][]=value[node];
for(int i=; i<edge[node].size(); i++)//考虑每个孩子,也是为了防止重复
for(int j=m; j>; j--) //必须从大到小,防止重复选取。
for(int k=; k<j; k++) //记得要留一个给自己
dp[node][j] =max( dp[node][j], dp[node][j-k] + dp[edge[node][i]][k]);//状态方程
return ;
}
int main()
{
//freopen("input.txt", "r", stdin);
int n, m, ai, bi;
while(cin>>n>>m)
{
memset(dp, , sizeof(dp));
for(int i=; i<N2; i++) //清除边
edge[i].clear(); for(int i=; i<=n; i++) //n个权值
cin>>value[i]; for(int i=; i<n; i++) //n-1条边
{
cin>>ai>>bi;
edge[ai].push_back(bi);
}
tree_dp(,m);
cout<<dp[][m]<<endl;
}
return ;
}

刷油漆

hihoCoder hiho一下 第十二周 #1055 : 刷油漆 (树上DP)的更多相关文章

  1. 【hiho一下第十二周】刷油漆

    [题目链接]:http://hihocoder.com/problemset/problem/1055 [题意] [题解] 设f[x][i]表示以第x个节点为根的子树; 不选x这个节点,然后子树里面选 ...

  2. HihoCoder第十二周:刷油漆

    #1055 : 刷油漆 时间限制:10000ms 单点时限:1000ms 内存限制:256MB 描述 上回说到,小Ho有着一棵灰常好玩的树玩具!这棵树玩具是由N个小球和N-1根木棍拼凑而成,这N个小球 ...

  3. hihoCoder #1055 : 刷油漆 [ 树形dp ]

    传送门 结果:Accepted     提交时间:2015-05-11 10:36:08 #1055 : 刷油漆 时间限制:10000ms 单点时限:1000ms 内存限制:256MB 描述 上回说到 ...

  4. hihocoder hiho一下 第二十六周 最小生成树一·(Prim算法)

    题目1 : 最小生成树一·Prim算法 时间限制:10000ms 单点时限:1000ms 内存限制:256MB 描述 最近,小Hi很喜欢玩的一款游戏模拟城市开放出了新Mod,在这个Mod中,玩家可以拥 ...

  5. hiho 1055 刷油漆 树形dp

    一个简单的树上的背包问题. 代码: #include <iostream> #include <cstdio> #include <cstring> #includ ...

  6. HihoCoder 1055 : 刷油漆 树形DP第一题(对象 点)

    刷油漆 时间限制:10000ms 单点时限:1000ms 内存限制:256MB 描述 上回说到,小Ho有着一棵灰常好玩的树玩具!这棵树玩具是由N个小球和N-1根木棍拼凑而成,这N个小球都被小Ho标上了 ...

  7. 201521123061 《Java程序设计》第十二周学习总结

    201521123061 <Java程序设计>第十二周学习总结 1. 本周学习总结 1.1 以你喜欢的方式(思维导图或其他)归纳总结多流与文件相关内容. 2. 书面作业 将Student对 ...

  8. 201521123072《java程序设计》第十二周学习总结

    201521123072<java程序设计>第十二周学习总结 1. 本周学习总结 1.1 以你喜欢的方式(思维导图或其他)归纳总结多流与文件相关内容. 2. 书面作业 将Student对象 ...

  9. 201521123038 《Java程序设计》 第十二周学习总结

    201521123038 <Java程序设计> 第十二周学习总结 1. 本周学习总结 1.1 以你喜欢的方式(思维导图或其他)归纳总结多流与文件相关内容. 2. 书面作业 将Student ...

随机推荐

  1. 网络应用(3):CDN与P2P的概念

    我前面说了流量的概念,流量是使用网络时经常要考虑的一个因素--如何才能更快的使用流量,如何才能节省流量使用的成本,对于这样的问题,你可能要了解一下什么是cdn,什么是p2p. (1)cdn是什么 cd ...

  2. java线程并发工具类CyclicBarrier、CountDownLatch及Semaphore

    一.CyclicBarrier   (原文链接:http://www.studyshare.cn/blog-front/blog/index ) 1.定义 CyclicBarrier是线程并发工具类之 ...

  3. BK Componet Monitor

    Apache a) 启动服务前将监听地址改成0.0.0.0 b) 确认在文件“/etc/httpd/conf.modules.d/00-base.conf“中有加载mod_status模块 c) 新建 ...

  4. CSS 框模型概述

    在 CSS 中,width 和 height 指的是内容区域的宽度和高度. 增加内边距.边框和外边距不会影响内容区域的尺寸,但是会增加元素框的总尺寸. 假设框的每个边上有 10 个像素的外边距和 5 ...

  5. CodeForces 110C 【构造】

    思路: 7越多越好,然后从7最多个数枚举过去,判断一下剩下的能不能用4解决就好了: #include <bits/stdc++.h> using namespace std; typede ...

  6. java知识点积累(一)

    知识点积累 1.关于final的重要知识点: final关键字可以用于成员变量.本地变量.方法以及类: final修饰的成员变量必须在声明时被初始化,或者在构造器中初始化,否则就会报编译错误: 不能够 ...

  7. 796D(bfs)

    题目链接: http://codeforces.com/problemset/problem/796/D 题意: 给出一颗 n 个节点树, 树枝连接的两个定点距离为 1, 树中有 k 个特殊点, 问最 ...

  8. 利用CSS制作脸书

    很多网站都支持图片上的头像框识别,鼠标在头像框处,会提示一些人物信息. 这次就利用CSS实现这样一个功能: div处主要包括两部分,一部分是图片:另一部分是链接以及脸框 <div class=& ...

  9. gulp前端自动化构建工具

    博主不易,不求赞赏,希望把自己遇到的难点写出来,以及希望自己能有能力写出一篇不错的博文. 前端构建工具本人 bootstrap+jquery用gulp vue+element 用webpack 引文 ...

  10. 关于JSON可能出现的错误,待更/todo

    今天写到webAppService.js的时候,用fs模块调用json,发现单引号的json被警告了. json就是一段有格式的字符串,如果数据的封装与解析都是我们自己做的时候,单引号和双引号是没啥关 ...