最快遍历完图中重要节点 树的直径 Codeforces 328 (Div. 2) D. Super M
2015-11-04 13:40
483 查看
http://codeforces.com/problemset/problem/592/D
树的直径补:http://www.cnblogs.com/celia01/archive/2012/07/30/2615842.html
题意
给你一棵树,树上有一些重要的点,超人必须要去。
然后让你选择一个点作为起点,使得从这个点开始遍历其他的重要的点要走的距离最小
如果有多个解,就输出最小的那个
题解:
相当于建一颗包含所有重要的点,但是大小最小的虚树,然后再那个虚树里面找到字典序最小的直径
然后答案就是2*边长-直径长度就好了
树的直径补:http://www.cnblogs.com/celia01/archive/2012/07/30/2615842.html
题意
给你一棵树,树上有一些重要的点,超人必须要去。
然后让你选择一个点作为起点,使得从这个点开始遍历其他的重要的点要走的距离最小
如果有多个解,就输出最小的那个
题解:
相当于建一颗包含所有重要的点,但是大小最小的虚树,然后再那个虚树里面找到字典序最小的直径
然后答案就是2*边长-直径长度就好了
#include <bits/stdc++.h> using namespace std; const int MAXX=130000; vector<int> adj[MAXX]; int dist[MAXX],mark[MAXX]; int sizee[MAXX];//该结点的子树下重要结点个数 int n,m,a,b; void dfs(int p,int v) { sizee[v]=0; if(mark[v]) sizee[v]=1; for(int j=0; j<adj[v].size(); j++) { int u=adj[v][j]; if(u!=p) { dist[u]=dist[v]+1;//计算树的直径 dfs(v,u); sizee[v]+=sizee[u]; } } } int main () { //freopen("in.txt","r",stdin); cin>>n>>m; for(int i=0; i<n-1; i++) { cin>>a>>b; a--; b--; adj[a].push_back(b); adj[b].push_back(a); } for(int i=0; i<m; i++) { cin>>a; a--; mark[a]=1; } dfs(-1,0); int v=-1; for(int i=0; i<n; i++) { if(mark[i]&&(v==-1||dist[i]>dist[v])) { v=i; } } memset(dist,0,sizeof(dist)); dfs(-1,v);//注意 int sum=0; int mx=0; for(int i=0; i<n; i++) { if(sizee[i]>0&&m-sizee[i]>0) sum+=2; if(mark[i]) mx=max(dist[i],mx); } for(int i=0; i<n; i++) { if(dist[i]==mx&&i<v&&mark[i]) { v=i; break; } } cout<<v+1<<'\n'<<sum-mx<<endl; return 0; }
相关文章推荐
- Android Platform Version 和 API Level对照
- 缓存应用--Memcached分布式缓存简介
- 网站计数器的设计
- spring mvc 图形验证码
- 数据库SQL中Like的用法总结
- exp/imp expdp/impdp乱码
- hdu 5532(最长上升子序列)
- Android中的ImageView和EditText(一)
- div+css 如何让背景层半透明 内容不透明 并且能兼容ie6,ie7,ie8,ff
- java.sql.Date 和java.util.Date 互转
- hdu 5532(最长上升子序列)
- 解决linux下ssh登陆远程服务器出错
- [LeetCode]:ZigZag Conversion
- R语言实例-数据过滤
- boost camp 分区失败处理方法
- 简单易学代码块(block)
- express默认配置文件app.js
- K Smallest Sums(优先队列+思维推广)
- Tomcat关闭过程(Tomcat源码解析四)
- C# 委托实例(跨窗体操作控件)