点击链接PAT甲级-AC全解汇总
题目:
A graph which is connected and acyclic can be considered a tree. The height of the tree depends on the selected root. Now you are supposed to find the root that results in a highest tree. Such a root is called the deepest root.
Input Specification:
Each input file contains one test case. For each case, the first line contains a positive integer N (≤104 ) which is the number of nodes, and hence the nodes are numbered from 1 to N. Then N−1 lines follow, each describes an edge by given the two adjacent nodes’ numbers.
Output Specification:
For each test case, print each of the deepest roots in a line. If such a root is not unique, print them in increasing order of their numbers. In case that the given graph is not a tree, print Error: K components where K is the number of connected components in the graph.
Sample Input 1:
5
1 2
1 3
1 4
2 5
- 1
- 2
- 3
- 4
- 5
Sample Output 1:
3
4
5
- 1
- 2
- 3
Sample Input 2:
5
1 3
1 4
2 5
3 4
- 1
- 2
- 3
- 4
- 5
Sample Output 2:
Error: 2 components
- 1
题意:
输入的是一棵树,找树的根使得深度最深
类似于图的最大生成树,但是因为输入的就是树,标记visited比较方便
思路:
第一次dfs,看有几个连通分量,同时找到最深的叶子,这些叶子肯定是可以做最深根的;
第二次dfs,从上一次dfs找到的最深叶子作为根,再找到的最深的叶子是刚才漏的;(因为第一次的起始点可能比较靠近它,所以才会漏,需要第二次dfs找回来);
两次最深根求并集就行了;
我的代码:
#include
using namespace std;
bool node[10010][10010]={false};
bool visited[10010]={false};
int N,deepest=0;
void DFS(int root,int root_depth,set<int>& candidate)
{
visited[root]=true;
if(root_depth>deepest)
{
deepest=root_depth;
candidate.clear();
candidate.insert(root);
}
else if(root_depth==deepest)
candidate.insert(root);
for(int next=1;next<=N;next++)
{
if(node[root][next]&&!visited[next])
DFS(next,root_depth+1,candidate);
}
}
int main()
{
cin>>N;
for(int i=0;i<N-1;i++)
{
int a,b;
cin>>a>>b;
node[a][b]=true;
node[b][a]=true;
}
//第一次DFS找到最大根候选集1,同时算有几个连通分量
int component=0;
set<int>candidate1;
for(int i=1;i<=N;i++)
{
if(visited[i])continue;
component++;
DFS(i,1,candidate1);
}
if(component>1)
{
printf("Error: %d components",component);
return 0;
}
//第二次DFS找到最大根候选集2
fill(visited,visited+10010,false);
deepest=0;
set<int>candidate2;
DFS(*candidate1.begin(),1,candidate2);
//两个候选集求并集
set<int>result;
set_union(candidate1.begin(), candidate1.end(),
candidate2.begin(), candidate2.end(),
inserter(result, result.begin()));
for(set<int>::iterator it=result.begin();it!=result.end();it++)
{
cout<<*it<<endl;
}
return 0;
}
- 1
- 2
- 3
- 4
- 5
- 6
- 7
- 8
- 9
- 10
- 11
- 12
- 13
- 14
- 15
- 16
- 17
- 18
- 19
- 20
- 21
- 22
- 23
- 24
- 25
- 26
- 27
- 28
- 29
- 30
- 31
- 32
- 33
- 34
- 35
- 36
- 37
- 38
- 39
- 40
- 41
- 42
- 43
- 44
- 45
- 46
- 47
- 48
- 49
- 50
- 51
- 52
- 53
- 54
- 55
- 56
- 57
- 58
- 59
- 60
- 61
- 62
- 63
- 64
- 65
- 66
- 67
- 68
- 69
- 70
- 71
评论记录:
回复评论: