二叉树两节点之间的最短距离

给定一个二叉树, 找到该树中两个指定节点间的最短距离

 

//   A
// B C
//D E F

// D E --> 2
// E F --> 4






解法一:先求两节点的最近公共祖先,然后层序遍历求三个节点所在位置的深度,然后距离加减就行
func main() {
    //按数组层序建立二叉树
    root:=createTree(0,[]int{1,2,3,4,5,6})
        
    //求公共祖先
    lca:=lowestCommonAncestor(root,root.Left,root.Right.Left)
    
    fmt.Println(Getdist(root,root.Left,root.Right.Left,lca))
}        

type TreeNode struct {
    Val int
    Left *TreeNode
    Right *TreeNode
}
// 按数组建立二叉树
func createTree(index int,nums []int) *TreeNode{
    if index>=len(nums){
        return nil
    }
    root:=&TreeNode{
        Val:   nums[index],
    }
    root.Left=createTree(index*2+1,nums)
    root.Right=createTree(index*2+2,nums)
    return root
}


//求最近公共祖先节点
func lowestCommonAncestor(root, p, q *TreeNode) *TreeNode {
    if root==nil{
        return nil
    }
    if root.Val==p.Val||root.Val==q.Val{// 如果p,q为根节点,则公共祖先为根节点
        return root
    }
    if find(root.Left,p)&&find(root.Left,q){// 如果p在左子树,并且q也在左子树,则在左子树查找公共祖先
        return lowestCommonAncestor(root.Left,p,q)
    }
    if find(root.Right,p)&&find(root.Right,q){
        return lowestCommonAncestor(root.Right,q,p)//如果p在右子树,并且q也在右子树,则在右子树查找公共祖先
    }
    return root // 如果p,q分属两侧,则公共祖先为根节点
}



//层序遍历求三个节点之间的距离
func Getdist(root,q,p,lca *TreeNode) int{
    que:=make([]*TreeNode,0)
    que=append(que,root)
    vis:=make([]int,3)
    depth:=0
    for len(que)!=0{
        size:=len(que)
        for i:=0;i<size;i++{
            front:=que[0]
            que=que[1:]
            if front==q{
                vis[0]=depth
            }
            if front==p{
                vis[1]=depth
            }
            if front==lca{
                vis[2]=depth
            }
            if front.Left!=nil{
                que=append(que,front.Left)
            }
            if front.Right!=nil{
                que=append(que,front.Right)
            }
        }
        depth++
    }
    return vis[0]+vis[1]-vis[2]
}

 

 

 

递归遍历二叉树,根据要寻找两个目标节点q,p和root节点的位置,分情况计算距离。

一、递归树的最小子结构,root、left、right节点

二、q,p节点中的一个为root节点(假设是q),那么q,p的距离就是p节点所在树的高度

 

三、q,p节点分别在root节点的左右子树中,那么q,p的距离就是两节点递归深度之和

 

https://blog.csdn.net/GlAz_C/article/details/123290205?utm_source=app&app_version=5.5.0&code=app_1562916241&uLinkId=usr1mkqgl919blen

 

 

 

func findDist(root,q,p *TreeNode,ans *int) int{
    if root==nil{
        return 0
    }
    left:=findDist(root.Left,q,p,ans)
    right:=findDist(root.Right,q,p,ans)
    if root==p||root==q{//root节点是q、p节点只其中一个,在继续判断子树是否存在另一个节点,并且q,p的距离就是高度差
        if left!=0{
            *ans=left
            return 0
        }
        if right!=0{
            *ans=right
            return 0
        }
        return 1
    }
    if left!=0&&right!=0{//q、p节点分别出现在左右两个子树
        *ans=left+right
        return 0
    }
    if left==0&&right==0{//p,q节点不在当前左右子树
        return 0
    }
    if left!=0{ //左子树出现目标节点,递归深度+1
        return left+1
    }
    return right+1
}

 

posted @ 2022-07-03 16:38  知道了呀~  阅读(242)  评论(0编辑  收藏  举报