T9-2 求二叉树中节点间的宽度
如下图所示的一棵二叉树的深度、宽度及结点间距离分别为:
深度:4 宽度:4(同一层最多结点个数)
结点间距离: ⑧→⑥为8 (3×2+2=8)
⑥→⑦为3 (1×2+1=3)
注:结点间距离的定义:由结点向根方向(上行方向)时的边数×2,
与由根向叶结点方向(下行方向)时的边数之和。

输入格式
输入文件第一行为一个整数n(1≤n≤100),表示二叉树结点个数。接下来的n-1行,表示从结点x到结点y(约定根结点为1),最后一行两个整数u、v,表示求从结点u到结点v的距离。
输出格式
三个数,每个数占一行,依次表示给定二叉树的深度、宽度及结点u到结点v间距离。
输入输出样例
输入 #1
10 1 2 1 3 2 4 2 5 3 6 3 7 5 8 5 9 6 10 8 6
输出 #1
4 4 8
#include <iostream> #include <algorithm> using namespace std;//91,需要深搜完善(5/10 已ac) struct node{ int father; //爸爸 int left; //左儿子 int right; //右儿子 int deep; //深度 int data; //记录节点走过没 }a[10001]; int sum[101]; int n,x,y,s,t,maxx=1; int lca(int x,int y){ //莽夫版lca(能看得懂版) a[x].data=1; //把x的节点记录已走过 while(a[x].father!=0){ //遍历至根节点 x=a[x].father; //更新遍历爸爸 a[x].data=1; //记录已走过 } while(a[y].data!=1){ //遍历至x节点已走过的节点,找到最近公共祖先 y=a[y].father; } return y; } void dfs(int id,int deep) { if(!id) return; a[id].deep=deep; maxx=max(maxx,deep); dfs(a[id].left,deep+1); dfs(a[id].right,deep+1); } int main(){ cin>>n; //初始化 a[1].deep=1; //根节点的深度为1 a[1].father=0; //根节点没有爸爸 //建树 for(int i=1;i<n;i++){ cin>>x>>y; if(a[x].left==0) //这个节点是否有左儿子 a[x].left=y; //变成左儿子 else //变成右儿子 a[x].right=y; a[y].father=x; /*a[y].deep=a[x].deep+1; //更新深度 //求深度 if(a[y].deep>maxx) //求出最大深度,第一个问题完成 maxx=a[y].deep;*/ } dfs(1,1);//求深度,与最大深度 cin>>s>>t; int f=lca(s,t),num=0,num1=0;//求最近公共祖先 while(s!=f){ //记录s到最近公共祖先有多少条边 s=a[s].father; num++; } num*=2; //结点间距离的定义:由结点向根方向(上行方向)时的边数×2, while(t!=f){ //记录t到最近公共祖先有多少条边 t=a[t].father; num1++; } //求宽度 for(int i=1;i<=n;i++) //把每一个深度有多少个节点记录 sum[a[i].deep]++; sort(sum+1,sum+1+100); cout<<maxx<<endl<<sum[100]<<endl<<num+num1; //sum[100]是最大的宽度节点个数 return 0; }