树形DP初探•总结
这几天,我自学了基础的树形DP,在此给大家分享一下我的心得。
首先,树形DP这种题主要就是解决有明确分层次且无环的树上动态规划的题。这种题型一般(注意只是基础、普通的情况下)用深度优先搜索来解决实际的DP部分,而且一般用记忆化搜索,因为树会有重复遍历节点的情况。在一棵树上针对普遍子树都满足根节点与两个子节点有特殊关系的,树形DP就应该是解决这道题的优选方法了。
讲完基础的定义,我们来讲几个挺有用的性质:
1、在一棵二叉树上,已知其中序遍历,它的任一个节点都可以成为它的根节点,对于每一个子树都成立。
2、在二叉树上任一个节点出发,都能遍历每一个位置。而且每个节点与另一个节点只有一条枝条连通。
3、树中一定无环。
4、多叉树转变成的二叉树中,原来的兄弟节点的兄弟还是自己的兄弟,孩子的孩子也还是自己的孩子的孩子,但是兄弟的孩子与自己无关,而且兄弟和自己是具有同等发展机会的。
5、树是具有递归性质的,无论是建树还是遍历,递归都有效。
6、……
各位大神如果有什么好的性质可以补充的话,欢迎在评论中补充。
接下来,这个存储树的方式也很讲技巧。判断节点数多不多,很少的话建议用邻接矩阵。
假如边数太多的话而且边与边之间联系比较大的话,建议用邻接表(链式前向星,数据大小要开2*n)。或者还可以用专门存树的各种方法,例如树根孩子表示法,双亲表示法,孩子兄弟表示法(重点)……
最后讲讲做这种题的步骤:
1、读题,分析。判断这道题到底是不是树形DP,还是披着树的外套的普通区间DP,还是其他树的问题。假如不是,马上找其他的方法。
2、想想怎么建树。首先该用什么来存储,判断这是一棵怎样的树。是单纯二叉树呢,或者单纯多叉树,还是多叉树转二叉树呢,这都需要经验判断,不同的题不一样。建树的过程可以用一个DFS(普通二叉树),也可以用建图的方法(多叉树),还可以用brother和child的方法(多叉转二叉)。
3、列出状态转移方程,并且用记忆化搜索来实现。选择返不返回值的时候因情况而定。
4、检查边界情况和初始化够不够周全,通常会在这里失分。还要想想有没有必要优化和有没有优化的方法,例如用指针存储等等。
讲几道例题:
1、加分二叉树
这道题分析后发现它并不是树形DP,只是有树的外形的区间DP,所以不满足第一步判断,撤。不过他的输出先序遍历还是挺值得理解一下的。
详情请看:http://www.cnblogs.com/Ronald-MOK1426/p/8445336.html
2、二叉苹果树
这道题是最基础的二叉树版树形DP。他用树根孩子表示法,很简单解决。
注意建树的时候记得删边,而且最后输出的是q+1。
详情请看:http://www.cnblogs.com/Ronald-MOK1426/p/8446738.html
3、最大利润
这道题是我们学校初三的一位大佬推荐的,尽管我们并没有做过(是JZOJ的题),但是也是多叉树中的一道好题。注意是双向边。有兴趣的同学可以去搜一下。
4、没有上司的舞会
这道题也是多叉树的一道经典题目,经过无数次改编。要用邻接表来储存。但是要注意初始化的时候小心点。后面用取点还是不取点的方法取到最大值。
详情请看:http://www.cnblogs.com/Ronald-MOK1426/p/8449790.html
5、选课
这道题是一道多叉树转二叉树的经典题。要用孩子兄弟表示法来存储。是一道有依赖性的问题。我比较看好他的改编版,要是我们要输出取了那些课程,那么这道题就变难了许多。我们可以通过原路返回的思想,一路找回相等的数值,那么就可以推出答案。同时也可以边记忆化搜索边推答案。
详情请看:http://www.cnblogs.com/Ronald-MOK1426/p/8448397.html
6、软件安装
这道题是选课的一个升级版,假如大家对选课非常熟悉和理解透彻的话,相信理解起来不是问题。但是初始化有点麻烦。
因为题目的意思是可能会出现互相依赖的情况,所以这道题是有环的。所以我们就要加入判环和缩点两个步骤。把判出来的环缩成一个新点。之后就和选课别无他样了。
详情请看:http://www.cnblogs.com/Ronald-MOK1426/p/8449686.html
说了这么多,总结一下。
这只是基础的树形DP,往下学肯定有各种的优化,本人在此先不作讲解,水平有限,见谅。
要是算过内存或者数组会爆的话,可以用链表、指针来优化一下存储的环节。
记忆化搜索部分一定要注意边界条件,否则会出错。
最后,讲一个自己总结的树形DP的套路。要是我们判断了一道题是树形DP,那么一般只可能3种存储:邻接矩阵、邻接表、孩子兄弟。然后记忆化部分就是简单的判断有无出现过,到边界了没有,假如都不满足,就搜索下一层,通过不断减少体积(分体积)的方法求出最值。(普通DP的基本操作)
请各位大神指正,谢谢大家!
树形DP初探•总结的更多相关文章
- 树形动态规划(树形DP)入门问题—初探 & 训练
树形DP入门 poj 2342 Anniversary party 先来个题入门一下~ 题意: 某公司要举办一次晚会,但是为了使得晚会的气氛更加活跃,每个参加晚会的人都不希望在晚会中见到他的直接上 ...
- poj3417 LCA + 树形dp
Network Time Limit: 2000MS Memory Limit: 65536K Total Submissions: 4478 Accepted: 1292 Descripti ...
- COGS 2532. [HZOI 2016]树之美 树形dp
可以发现这道题的数据范围有些奇怪,为毛n辣么大,而k只有10 我们从树形dp的角度来考虑这个问题. 如果我们设f[x][k]表示与x距离为k的点的数量,那么我们可以O(1)回答一个询问 可是这样的话d ...
- 【BZOJ-4726】Sabota? 树形DP
4726: [POI2017]Sabota? Time Limit: 20 Sec Memory Limit: 128 MBSec Special JudgeSubmit: 128 Solved ...
- 树形DP+DFS序+树状数组 HDOJ 5293 Tree chain problem(树链问题)
题目链接 题意: 有n个点的一棵树.其中树上有m条已知的链,每条链有一个权值.从中选出任意个不相交的链使得链的权值和最大. 思路: 树形DP.设dp[i]表示i的子树下的最优权值和,sum[i]表示不 ...
- 树形DP
切题ing!!!!! HDU 2196 Anniversary party 经典树形DP,以前写的太搓了,终于学会简单写法了.... #include <iostream> #inclu ...
- BZOJ 2286 消耗战 (虚树+树形DP)
给出一个n节点的无向树,每条边都有一个边权,给出m个询问,每个询问询问ki个点,问切掉一些边后使得这些顶点无法与顶点1连接.最少的边权和是多少.(n<=250000,sigma(ki)<= ...
- POJ2342 树形dp
原题:http://poj.org/problem?id=2342 树形dp入门题. 我们让dp[i][0]表示第i个人不去,dp[i][1]表示第i个人去 ,根据题意我们可以很容易的得到如下递推公式 ...
- hdu1561 The more, The Better (树形dp+背包)
题目链接:http://acm.split.hdu.edu.cn/showproblem.php?pid=1561 思路:树形dp+01背包 //看注释可以懂 用vector建树更简单. 代码: #i ...
随机推荐
- SQL之case when then用法详解
case具有两种格式.简单case函数和case搜索函数. <span style="font-size:14px;">--简单case函数 case sex when ...
- 【第五周】alpha发布之小组评论
对于昨天的阿尔法发布,有那么几点需要说一下: 1,对这次阿尔法发布的过程,我们组还是基本顺利的,由于之前吃过亏,这次我提前试用了一下投影仪,做了些调试,之后的发布过程起码设备上是正常的. 2,我们的项 ...
- 自签证书 doesn't match any of the subject alternative names
出现这个的原因是https中的域名或者IP,与证书中登记的不一致. 如果是自签证书的话,可以根据具体需要重新生成证书. 还有一种解决方案是在java中跳过这个检查. 绕过检查分两类,一个是绕过证书在C ...
- 微信小程序组件 自定义单选
<view class='userperson'> <view class='f30 flexca'>请选择您的注册身份</view> <view class ...
- Java NIO中的Buffer
简介 Buffer缓冲区,首先要弄明白的是,缓冲区是怎样一个概念.它其实是缓存的一种,我们常说的缓存,包括保存在硬盘上的浏览器缓存,保存在内存中的缓存(比如Redis.memcached).Buffe ...
- 【刷题】洛谷 P4716 【模板】最小树形图
题目背景 这是一道模板题. 题目描述 给定包含 \(n\) 个结点, \(m\) 条有向边的一个图.试求一棵以结点 \(r\) 为根的最小树形图,并输出最小树形图每条边的权值之和,如果没有以 \(r\ ...
- 已知UIScrollView放大后的Frame和放大之前的Frame计算放大的瞄点坐标
有时候在缩放后,需要知道该次缩放是在哪个坐标开始缩放的.如上篇已知缩放的点,然后在该点对其缩放.本篇其实是逆运算 (x,y)就是当初在该点进行缩放 化简之后很简单,代码如下: func getZoom ...
- Android 解决ScrollView嵌入ListView | GridView | ScrollView显示问题
一.ScrollView中嵌套ListView ScrollView和ListView都是滚动结构,很明显如果在ScrollView中加入ListView,可以预见性的知道,肯定会有显示/滚动的问题, ...
- 洛谷P4609 [FJOI2016]建筑师 【第一类斯特林数】
题目链接 洛谷P4609 题解 感性理解一下: 一神带\(n\)坑 所以我们只需将除了\(n\)外的\(n - 1\)个元素分成\(A + B - 2\)个集合,每个集合选出最大的在一端,剩余进行排列 ...
- 电子商务(电销)平台中财务模块(Finance)数据库设计明细
以下是自己在电子商务系统设计中的数据库设计经验总结,而今发表出来一起分享,如有不当,欢迎跟帖讨论~ 资金账户表 (finance_account)|-- 自动编号|-- 用户编号|-- 预付款 (ad ...