zoukankan      html  css  js  c++  java
  • 2021-02-07:给定两棵二叉树的头节点head1和head2,如何判断head1中是否有某个子树的结构和head2完全一样?

    福哥答案2021-02-07:

    对head1和head2序列化为str1和str2。然后用kmp算法去判断str2是否是str1的子串。如果是,head2是子树;如果不是,head2不是子树。

    代码用golang编写,代码如下:

    package main
    
    import "fmt"
    
    func main() {
        root := &TreeNode{}
        root.Val = 1
    
        root.Left = &TreeNode{}
        root.Left.Val = 2
    
        root.Right = &TreeNode{}
        root.Right.Val = 3
    
        root.Left.Right = &TreeNode{}
        root.Left.Right.Val = 4
    
        root.Right.Left = &TreeNode{}
        root.Right.Left.Val = 5
    
        fmt.Println(IsSubTree(root, root.Right))
    
    }
    
    type TreeNode struct {
        Val   int
        Left  *TreeNode
        Right *TreeNode
    }
    
    //序列化
    func serialize(head *TreeNode) string {
        ansVal := ""
        ans := &ansVal
        process(head, ans)
        return (*ans)[1:]
    }
    
    func process(head *TreeNode, ans *string) {
        if head == nil {
            *ans += ",N"
            return
        }
        *ans += fmt.Sprintf(",%d", head.Val)
        process(head.Left, ans)
        //*ans += fmt.Sprintf(",%d", head.Val)
        process(head.Right, ans)
        //*ans += fmt.Sprintf(",%d", head.Val)
    }
    func getNextArr(m string) []int {
        mLen := len(m)
        if mLen == 1 {
            return []int{-1}
        }
        ret := make([]int, mLen)
        ret[0] = -1
        cn := 0
        for i := 2; i < mLen; i++ {
            if m[i] == m[cn] {
                cn++
                ret[i] = cn
                i++
            } else if cn > 0 {
                cn = ret[cn]
            } else {
                ret[i] = 0
                i++
            }
        }
        return ret
    }
    
    //求子串位置
    func kmp(s string, m string) int {
        sLen := len(s)
        mLen := len(m)
        if sLen < mLen {
            return -1
        }
        next := getNextArr(m)
        x := 0
        y := 0
        for x < sLen && y < mLen {
            if s[x] == m[y] {
                x++
                y++
            } else if next[y] >= 0 {
                y = next[y]
            } else {
                x++
            }
        }
        if y == mLen {
            return x - y
        } else {
            return -1
        }
    }
    
    //求是否是子树
    func IsSubTree(head1 *TreeNode, head2 *TreeNode) bool {
        if head2 == nil {
            return true
        }
        if head1 == nil {
            return false
        }
        if kmp(serialize(head1), serialize(head2)) >= 0 {
            return true
        } else {
            return false
        }
    }
    

      

    执行结果如下:


    ***
    [评论](https://user.qzone.qq.com/3182319461/blog/1612654678)

  • 相关阅读:
    userInteractionEnabled
    shareInstance
    UISearchBar
    IOS开发之UIView总结1
    IOS Table中Cell的重用reuse机制分析
    显示/隐藏Mac隐藏文件
    iOS视图控制对象生命周期-init、viewDidLoad、viewWillAppear、viewDidAppear、viewWillDisappear、viewDidDisappear的区别及用途
    2020/4/7
    2020/4/6
    2020/4/4
  • 原文地址:https://www.cnblogs.com/waitmoon/p/14386781.html
Copyright © 2011-2022 走看看