#include<iostream>
#include<vector>
#include<set>
#include<algorithm>
using namespace std;//一般转几个圈是段错误没结果
int maxh=0,visit[10010]={0};//maxh rct
vector<vector<int>>vv;
vector<int> temp;//temp条件重置
set<int>s;
void dfs(int f,int h){//存储最高结点
//end
visit[f]=1;
if(h>maxh){
maxh=h;
temp.clear();//只存最高结点不存路径
temp.push_back(f);
}
else if(h==maxh){
temp.push_back(f);
}
for(int i=0;i<vv[f].size();i++){
if(visit[vv[f][i]]==0)
dfs(vv[f][i],h+1);
}
/*for(int i = 0; i < vv[f].size(); i++) {
if(visit[vv[f][i]] == 0)
dfs(vv[f][i], h + 1);
} */
}
/*
void dfs(int node, int height) {
if(height > maxh) {
temp.clear();
temp.push_back(node);
maxh = height;
} else if(height == maxh){
temp.push_back(node);
}
visit[node] = 1;
for(int i = 0; i < vv[node].size(); i++) {
if(visit[vv[node][i]] == 0)
dfs(vv[node][i], height + 1);
}
}*/
int main(){
int n,_1,_2,s1,cnt=0;
cin>>n;
vv.resize(n+1);
for(int i=0;i<n-1;i++){
cin>>_1>>_2;
vv[_1].push_back(_2);
vv[_2].push_back(_1);//当成图来存储的因为还要从其他节点开始可以返回去,所以要标记否则会出现死循环(注意)
}
for(int i=1;i<=n;i++){
if(visit[i]==0){
dfs(i,1);
//debug
//for(int j=0;j<temp.size();j++)
//printf("%d",temp[j]);
if(i==1){
if(temp.size()!=0)s1=temp[0];//条件注意
for(int j=0;j<temp.size();j++)
s.insert(temp[j]);
}
cnt++;
}
}
if(cnt!=1){
printf("Error: %d components",cnt);
}
else{
fill(visit,visit+10010,0);
maxh=0;temp.clear();
dfs(s1,1);
for(int i=0;i<temp.size();i++){
s.insert(temp[i]);
}
for(auto it=s.begin();it!=s.end();it++){//auto
cout<<*it<<endl;//只能用迭代器???(注意)
}
}
return 0;
}
总结
1.之前有的dfs没写终止条件也没发生段错误是因为存储的路径本质上是一个单向图,而此时是双向的,必须有标记,哪个访问过,哪个没有,否则会出现死循环段错误
2. set map遍历时都是用迭代器遍历 注意是*it
3.//一般转几个圈是段错误没结果 死循环or迭代器错误
4.求树图的最高层数只要dfs两次即可如果只 有⼀一个,就两次深度优先搜索,先从⼀一个结点dfs后保留留最⾼高⾼高度拥有的结点们,然后从这些结点中的 其中任意⼀一个开始dfs得到最⾼高⾼高度的结点们,这两个结点集合的并集就是所求
英语
问题
思路总结