版权声明:本文为博主原创文章,未经博主允许不得转载。

Rebuilding Roads
Time Limit: 1000MS   Memory Limit: 30000K
Total Submissions: 8227   Accepted: 3672

Description

The cows have reconstructed Farmer John's farm, with its N barns (1 <= N <= 150, number 1..N) after the terrible earthquake last May. The cows didn't have time to rebuild any extra roads, so now there is exactly one way to get from any given barn to any other barn. Thus, the farm transportation system can be represented as a tree.

Farmer John wants to know how much damage another earthquake could do. He wants to know the minimum number of roads whose destruction would isolate a subtree of exactly P (1 <= P <= N) barns from the rest of the barns.

Input

* Line 1: Two integers, N and P

* Lines 2..N: N-1 lines, each with two integers I and J. Node I is node J's parent in the tree of roads.

Output

A single line containing the integer that is the minimum number of roads that need to be destroyed for a subtree of P nodes to be isolated. 

Sample Input

11 6
1 2
1 3
1 4
1 5
2 6
2 7
2 8
4 9
4 10
4 11

Sample Output

2

Hint

[A subtree with nodes (1, 2, 3, 6, 7, 8) will become isolated if roads 1-4 and 1-5 are destroyed.] 

Source

题意:

给你一棵树,求最少剪掉几条边使能够得到一个p个节点的树。

思路:

用dp[i][j]代表以i为根的子树要变成j个节点需要剪掉的边数。

考虑子节点的时候不用考虑它与父节点的那条边,就当不存在,那么最后求的的最小边数加1就行了。
考虑一个节点时,有两种选择,要么剪掉跟子节点相连的边,则dp[i][j] = dp[i][j]+1;

要么不剪掉,则dp[i][j] = max(dp[i][j], dp[i][k]+dp[son][j-k]);

然后随便以一条边dfs求解就行了。

为什么可以这样求解呢。

对于树上的一个节点。要么在待求解子树中。要么不在。在的话即dp[i][p]中。不然的话就肯定在其它子树上了。

详细见代码:

  1. #include <iostream>
  2. #include<stdio.h>
  3. #include<string.h>
  4. using namespace std;
  5. const int maxn=250;
  6. const int INF=0x3f3f3f3f;
  7. struct node
  8. {
  9. int v;
  10. node *next;
  11. } edge[maxn<<1],*head[maxn];
  12. int n,m,cnt,dp[maxn][maxn];
  13. void adde(int u,int v)
  14. {
  15. edge[cnt].v=v;
  16. edge[cnt].next=head[u];
  17. head[u]=&edge[cnt++];
  18. }
  19. void dfs(int fa,int u)
  20. {
  21. int i,j,v,mm=INF;
  22. node *p;
  23. dp[u][1]=0;
  24. for(p=head[u];p!=NULL;p=p->next)
  25. {
  26. v=p->v;
  27. if(v==fa)
  28. continue;
  29. dfs(u,v);
  30. for(i=m;i>=1;i--)//01背包。从大到小装
  31. {
  32. mm=dp[u][i]+1;//不要该子树.
  33. for(j=1;j<i;j++)//要该子树
  34. mm=min(mm,dp[u][j]+dp[v][i-j]);
  35. dp[u][i]=mm;
  36. }
  37. }
  38. }
  39. int main()
  40. {
  41. int i,u,v,ans;
  42. while(~scanf("%d%d",&n,&m))
  43. {
  44. cnt=0;
  45. memset(head,0,sizeof head);
  46. memset(dp,0x3f,sizeof dp);
  47. for(i=1;i<n;i++)
  48. {
  49. scanf("%d%d",&u,&v);
  50. adde(u,v);
  51. adde(v,u);
  52. }
  53. dfs(1,1);
  54. ans=dp[1][m];
  55. for(i=1;i<=n;i++)
  56. ans=min(ans,dp[i][m]+1);//加1是因为根转移了
  57. printf("%d\n",ans);
  58. }
  59. return 0;
  60. }

DP Intro - poj 1947 Rebuilding Roads(树形DP)的更多相关文章

  1. POJ 1947 Rebuilding Roads 树形DP

    Rebuilding Roads   Description The cows have reconstructed Farmer John's farm, with its N barns (1 & ...

  2. POJ 1947 Rebuilding Roads 树形dp 难度:2

    Rebuilding Roads Time Limit: 1000MS   Memory Limit: 30000K Total Submissions: 9105   Accepted: 4122 ...

  3. DP Intro - poj 1947 Rebuilding Roads

    算法: dp[i][j]表示以i为根的子树要变成有j个节点的状态需要减掉的边数. 考虑状态转移的时候不考虑i的父亲节点,就当不存在.最后统计最少减去边数的 时候+1. 考虑一个节点时,有两种选择,要么 ...

  4. 树形dp(poj 1947 Rebuilding Roads )

    题意: 有n个点组成一棵树,问至少要删除多少条边才能获得一棵有p个结点的子树? 思路: 设dp[i][k]为以i为根,生成节点数为k的子树,所需剪掉的边数. dp[i][1] = total(i.so ...

  5. POJ 1947 Rebuilding Road(树形DP)

    Description The cows have reconstructed Farmer John's farm, with its N barns (1 <= N <= 150, n ...

  6. [poj 1947] Rebuilding Roads 树形DP

    Rebuilding Roads Time Limit: 1000MS Memory Limit: 30000K Total Submissions: 10653 Accepted: 4884 Des ...

  7. POJ 1947 Rebuilding Roads (树dp + 背包思想)

    题目链接:http://poj.org/problem?id=1947 一共有n个节点,要求减去最少的边,行号剩下p个节点.问你去掉的最少边数. dp[u][j]表示u为子树根,且得到j个节点最少减去 ...

  8. POJ1947 - Rebuilding Roads(树形DP)

    题目大意 给定一棵n个结点的树,问最少需要删除多少条边使得某棵子树的结点个数为p 题解 很经典的树形DP~~~直接上方程吧 dp[u][j]=min(dp[u][j],dp[u][j-k]+dp[v] ...

  9. POJ 1947 Rebuilding Roads

    树形DP..... Rebuilding Roads Time Limit: 1000MS Memory Limit: 30000K Total Submissions: 8188 Accepted: ...

随机推荐

  1. MyBatis和Hibernate相比较

    作者:乌拉拉链接:http://www.zhihu.com/question/21104468/answer/58579295 1.开发对比开发速度 Hibernate的真正掌握要比Mybatis来得 ...

  2. JavaScript语言精粹 笔记01 语法 对象

    内容比较简单,只是从头梳理一下JS的知识 语法空白标识符数字字符串语句 对象对象字面量检索更新引用原型反射枚举删除减少全局变量污染  语法 1 空白 空白可能表现为格式化字符或注释的形式.空白通常没有 ...

  3. sql语句有几种写法

    sql语句有几种写法 1:SELECT * FROM tablename ORDER BY RAND() LIMIT 想要获取的数据条数: 2:SELECT *FROM `table` WHERE i ...

  4. ssh关于含有外键的传值中无法识别正确的action的原因和解决办法

    在含有外键的表中,要保存一个值到这个外键时:逻辑思路:需要先将jsp页面的值传到相应的action中,在这个action中需要引入这个外键的实体层和DAO层(DAO层只需set方法),在执行函数中对于 ...

  5. 微信小程序中使用阿里字体图标

    在微信小程序中使用阿里字体图标 ,不通过转换成base64的方式实现. 为了美化微信小程序,可以适当的使用一些小图标,这样体验也更友好些,于是决定使用常用的字体图标. 下载图标 首先在阿里字体图标查找 ...

  6. Android-xx倍图

    图片文件夹对应倍图关系: ldpi 0.75 倍图 mdpi   1.0 倍图   hdpi    1.5 倍图 xhdpi  2.0 倍图 xxhdpi    3.0 倍图 xxxhdpi  4.0 ...

  7. Arcgis Android 坐标转换

    http://spatialreference.org/首先,在上面的网站查出现有的坐标srid,然后查出目标Srid. 参考api 示例代码 Point point = new Point(120. ...

  8. jQuery制作多表格固定表头、切换表头的特效

    做了好几天的固定表头特效,总算是搞定了.先说明一下基本功能:我们在一个网页上浏览很多份表格数据的时候,肯定会碰到很多分不清表头,也分不清表 格是哪个的情况,这个时候我们就希望能有一种功能,就是我们再下 ...

  9. 通用性站点管理后台(Bee OPOA Platform) (5)- 【扩展】基于WebSocket的监视Sql执行功能

    开始 底层的东西总是很类似, 看了园里的Fish-Li的一系列文章, 写得真好, 无论是风格还是内容. 本来也想想方便点就用remoting实现监视功能算了, 但这样就需要一个Winform的项目了. ...

  10. [Erlang00]:gen_server:reply/2

    --- gen_server:reply/2 reply(Client, Reply) –> Result      Types:     Client - see below     Repl ...