【PAT甲级】1021 Deepest Root (25 分)(暴力,DFS)
题意:
输入一个正整数N(N<=10000),然后输入N-1条边,求使得这棵树深度最大的根节点,递增序输出。如果不是一棵树,输出这张图有几个部分。
trick:
时间比较充裕数据可能也不是很极限,所以用了一个暴力的手段。直接枚举度数为1的点进行深度优先搜索,如果递归了一万次还没有return就当它有环。(这道题的数据不存在只有一个带有自环的部分,即如有自环图必定不止一个)正解应当是dfs一次以后找到一些可能是最深根的叶子结点们,然后对这些叶子节点们依次dfs,再找到对应的一些叶子节点们。成对的叶子结点并且长度最大的就是答案。(最深根一定是成对成对的)(正解待补)
AAAAAccepted code:
1 #include<bits/stdc++.h> 2 using namespace std; 3 vector<int>edg[10007]; 4 int vis[10007]; 5 int deg[10007]; 6 int ans[10007]; 7 int tmp=0; 8 int mx=0; 9 int num=0; 10 int dfs(int x,int fa){ 11 num++; 12 if(num>10000)//断言出现自环,一共只有N个点 13 return 1; 14 vis[x]=1; 15 ++tmp; 16 mx=max(mx,tmp); 17 for(auto it:edg[x]) 18 if(it!=fa) 19 dfs(it,x); 20 --tmp; 21 return 0; 22 } 23 int main(){ 24 int n; 25 cin>>n; 26 for(int i=1;i<n;++i){ 27 int u,v; 28 cin>>u>>v; 29 edg[u].push_back(v); 30 edg[v].push_back(u); 31 ++deg[u]; 32 ++deg[v]; 33 } 34 int cnt=0; 35 int mxx=0; 36 int flag2=0; 37 for(int i=1;i<=n;++i){ 38 tmp=0; 39 mx=0; 40 if(deg[i]==1){//叶子结点才可能作为最深根出现 41 if(!vis[i]) 42 ++cnt; 43 num=0; 44 dfs(i,0); 45 ans[i]=mx; 46 mxx=max(mxx,mx); 47 } 48 } 49 for(int i=1;i<=n;++i) 50 if(!vis[i]){ 51 num=0; 52 dfs(i,0); 53 ++cnt; 54 } 55 int flag=0; 56 if(cnt==1){ 57 for(int i=1;i<=n;++i) 58 if(ans[i]==mxx){ 59 if(flag) 60 cout<<"\n"; 61 cout<<i; 62 flag=1; 63 } 64 } 65 else 66 cout<<"Error: "<<cnt<<" components"; 67 return 0; 68 }
保持热爱 不懈努力
不试试看怎么知道会失败呢(划掉)
世上无难事 只要肯放弃(划掉)