当时比赛的时候我们找出来只要求出树的最长的边的节点数ans,如果要访问点的个数n小于ans距离直接就是n-1

如果大于的话就是(n-ans)*2+ans-1,当时求树的直径难倒我们了,都不会树形dp

选一个点当根每次求出一点到子节点的最大距离和次大距离,两个的和最大的就是树的直径

还在网上看到一种方法,任意一点广搜达到最远点max,再从max广搜,到达最远点就是树的直径

自己想了想这种方法:如果中间有点有分支的话,那么这点的最大分支一定是到max的

但是它的次大分支就不一定是到起点的,所以从max搜的话肯定是到这点的次大分支,就是直径了

  1. #include<stdio.h>
  2. #include<string.h>
  3. #define N 100001
  4. int head[N],num,ins[N],n;
  5. struct edge
  6. {
  7. int ed,next;
  8. }E[N*2];
  9. void addedge(int x,int y)
  10. {
  11. E[num].ed=y;
  12. E[num].next=head[x];
  13. head[x]=num++;
  14. }
  15. int dis;
  16. int dist(int u)
  17. {
  18. ins[u]=1;
  19. int max=0,mmax=0;
  20. for(int i=head[u];i!=-1;i=E[i].next)
  21. {
  22. int v=E[i].ed;
  23. if(ins[v]==1)continue;
  24. int temp=dist(v);
  25. if(temp>mmax)
  26. {
  27. max=mmax;
  28. mmax=temp;
  29. }
  30. else if(temp>max)
  31. {
  32. max=temp;
  33. }
  34. }
  35. if(dis<(mmax+max+1))
  36. dis=mmax+max+1;
  37. return mmax+1;
  38. }
  39. int main()
  40. {
  41. int i,m,x,y,t;
  42. scanf("%d",&t);
  43. while(t--)
  44. {
  45. scanf("%d%d",&n,&m);
  46. memset(head,-1,sizeof(head));
  47. num=0;
  48. for(i=0;i<n-1;i++)
  49. {
  50. scanf("%d%d",&x,&y);
  51. addedge(x,y);
  52. addedge(y,x);
  53. }
  54. memset(ins,0,sizeof(ins));
  55. dis=0;
  56. dist(1);
  57. for(i=1;i<=m;i++)
  58. {
  59. scanf("%d",&x);
  60. if(x<=dis)
  61. printf("%d\n",x-1);
  62. else printf("%d\n",dis+(x-dis)*2-1);
  63. }
  64. }
  65. return 0;
  66. }
  1. #include<stdio.h>
  2. #include<queue>
  3. #include<string.h>
  4. #define N 100001
  5. using namespace std;
  6. int head[N],num,vis[N],n;
  7. struct edge
  8. {
  9. int ed,next;
  10. }E[N*2];
  11. struct node
  12. {
  13. int x,w;
  14. }cur,next;
  15. void addedge(int x,int y)
  16. {
  17. E[num].ed=y;
  18. E[num].next=head[x];
  19. head[x]=num++;
  20. }
  21. int dist()
  22. {
  23. int i,v;
  24. memset(vis,0,sizeof(vis));
  25. queue<node>Q1,Q2;
  26. cur.x=1;
  27. Q1.push(cur);
  28. while(!Q1.empty())
  29. {
  30. cur=Q1.front();
  31. Q1.pop();
  32. vis[cur.x]=1;
  33. for(i=head[cur.x];i!=-1;i=E[i].next)
  34. {
  35. next.x=v=E[i].ed;
  36. if(vis[v]==0)
  37. Q1.push(next);
  38. }
  39. }
  40. cur.w=1;
  41. Q2.push(cur);//广搜最后出来的点一点是最远点
  42. memset(vis,0,sizeof(vis));
  43. while(!Q2.empty())
  44. {
  45. cur=Q2.front();
  46. Q2.pop();
  47. vis[cur.x]=1;
  48. for(i=head[cur.x];i!=-1;i=E[i].next)
  49. {
  50. next.x=v=E[i].ed;
  51. next.w=cur.w+1;
  52. if(vis[v]==0)
  53. Q2.push(next);
  54. }
  55. }
  56. return cur.w;
  57. }
  58. int main()
  59. {
  60. int i,m,x,y,t;
  61. scanf("%d",&t);
  62. while(t--)
  63. {
  64. scanf("%d%d",&n,&m);
  65. memset(head,-1,sizeof(head));
  66. num=0;
  67. for(i=0;i<n-1;i++)
  68. {
  69. scanf("%d%d",&x,&y);
  70. addedge(x,y);
  71. addedge(y,x);
  72. }
  73. int dis=dist();
  74. for(i=1;i<=m;i++)
  75. {
  76. scanf("%d",&x);
  77. if(x<=dis)
  78. printf("%d\n",x-1);
  79. else printf("%d\n",dis+(x-dis)*2-1);
  80. }
  81. }
  82. return 0;
  83. }

hdu 4607 (树形DP)的更多相关文章

  1. hdu 4607 树形dp 树的直径

    题目大意:给你n个点,n-1条边,将图连成一棵生成树,问你从任意点为起点,走k(k<=n)个点,至少需要走多少距离(每条边的距离是1): 思路:树形dp求树的直径r: a:若k<=r+1 ...

  2. hdu 4123 树形DP+RMQ

    http://acm.hdu.edu.cn/showproblem.php? pid=4123 Problem Description Bob wants to hold a race to enco ...

  3. HDU 1520 树形dp裸题

    1.HDU 1520  Anniversary party 2.总结:第一道树形dp,有点纠结 题意:公司聚会,员工与直接上司不能同时来,求最大权值和 #include<iostream> ...

  4. HDU 1561 树形DP入门

    The more, The Better Time Limit: 6000/2000 MS (Java/Others)    Memory Limit: 32768/32768 K (Java/Oth ...

  5. HDU 2196树形DP(2个方向)

    HDU 2196 [题目链接]HDU 2196 [题目类型]树形DP(2个方向) &题意: 题意是求树中每个点到所有叶子节点的距离的最大值是多少. &题解: 2次dfs,先把子树的最大 ...

  6. HDU 1520 树形DP入门

    HDU 1520 [题目链接]HDU 1520 [题目类型]树形DP &题意: 某公司要举办一次晚会,但是为了使得晚会的气氛更加活跃,每个参加晚会的人都不希望在晚会中见到他的直接上司,现在已知 ...

  7. codevs 1380/HDU 1520 树形dp

    1380 没有上司的舞会 时间限制: 1 s 空间限制: 128000 KB 题目等级 : 钻石 Diamond 题解 查看运行结果 回到问题 题目描述 Description Ural大学有N个职员 ...

  8. HDU 5834 [树形dp]

    /* 题意:n个点组成的树,点和边都有权值,当第一次访问某个点的时候获得利益为点的权值 每次经过一条边,丢失利益为边的权值.问从第i个点出发,获得的利益最大是多少. 输入: 测试样例组数T n n个数 ...

  9. hdu 4267 树形DP

    思路:先dfs一下,找出1,n间的路径长度和价值,回溯时将该路径长度和价值清零.那么对剩下的图就可以直接树形dp求解了. #include<iostream> #include<al ...

随机推荐

  1. MapReduce编程系列 — 3:数据去重

    1.项目名称: 2.程序代码: package com.dedup; import java.io.IOException; import org.apache.hadoop.conf.Configu ...

  2. 类似百度文库pdf2swf+flexpaper解决pdf在线阅读的效果

    1:工具准备swftools.exe 下载http://www.swftools.org/download.html 安装至D盘SWFTools提供了一系列将各种文件转成swf的工具:font2swf ...

  3. objective-C 自定义对象归档的实现

    自定义对象要实现归档必须实现NSCoding协议 NSCoding协议有两个方法,encodeWithCoder方法对对象的属性数据做编码处理,initWithCoder解码归档数据来初始化对象. # ...

  4. 【iOS开发】iOS7 兼容及部分细节

    1:statusBar字体为白色 在plist里面设置View controller-based status bar appearance 为 NO:设置statusBarStyle 为 UISta ...

  5. (转)CAP理论十二年回顾:"规则"变了

    编者按:由InfoQ主办的全球架构师峰会将于2012年8月10日-12日在深圳举行,为了更好地诠释架构的意义.方法和实践,InfoQ中文站近期会集中发布一批与架构相关的文章,本篇即为其中之一.Info ...

  6. MAC 上搭建lua环境

    一.下载并安装 (1)最新release版下载地址 http://www.lua.org/ftp/lua-5.3.1.tar.gz (2)编译 Building Lua is implemented ...

  7. eclipse 中创建maven web项目

    Maven的Eclipse插件m2eclipse在线安装地址 http://m2eclipse.sonatype.org/sites/m2e:我又试了link方式安装也没什么作用,不知怎么回事? 还有 ...

  8. vbox android x86 分辨率

    D:\Program Files\Oracle\VirtualBox>VBoxManage setextradata "android" "CustomVideoM ...

  9. 读取Excel任务列表并显示在Outlook日历上

    前几天,公司发了一个任务安排,时间不固定,但要求准时到,为了给自己加一个提醒,也为了回顾一下以前的技术,特做了一个Demo. 读取Excel就不多说了,代码很简单,但支持老版本Excel和的版本Exc ...

  10. Linux 根文件系统制作

    1.创建根文件目录 mkdir rootfs(名字是随便取的) 2.创建子目录 cd rootfs mkdir bin dev etc lib proc sbin sys usr mnt tmp va ...