【二叉树】删除二叉搜索树中的节点

0x00 题目

定一个二叉搜索树的根节点 root 和一个值 key
删除二叉搜索树中的 key 对应的节点
并保证二叉搜索树的 性质 不变
返回二叉搜索树(有可能被更新)的 根节点 的引用

一般来说,删除节点可分为 两个 步骤:
首先 找到 需要删除的节点
如果找到了 删除


0x01 思路

删除节点,要分以下几种情况:

1.节点恰好是 末端 节点,两个 子节点 都为
直接返回 nil,替换当前节点

if (root.left == nil && root.right == nil) {
    return nil
}

2.节点只有 一个 非空 子节点
那么要让这个孩子接替自己的位置

if (root.left == nil) { return root.right }
if (root.right == nil) { return root.left }

3.节点有 两个 子节点,为了不破坏 BST 的性质
必须找到 左子树最大 的那个节点
或者 右子树最小 的那个节点来接替自己

// 找到右子树的最小节点
let minNode = getMinNode(root.right!)

// 把 root 改成 minNode
root.val = minNode.val

// 转而去删除 minNode
root.right = deleteNode(root.right, minNode.val)

0x02 解法

语言:Swift

树节点:TreeNode

public class TreeNode {
    public var val: Int
    public var left: TreeNode?
    public var right: TreeNode?
    public init() { self.val = 0; self.left = nil; self.right = nil; }
    public init(_ val: Int) { self.val = val; self.left = nil; self.right = nil; }
    public init(_ val: Int, _ left: TreeNode?, _ right: TreeNode?) {
        self.val = val
        self.left = left
        self.right = right
    }
}

解法:

func deleteNode(_ root: TreeNode?, _ key: Int) -> TreeNode? {
    guard let root = root else { return nil }
    
    // 比根节点大,往右边找
    if (root.val < key) {
        root.right = deleteNode(root.right, key)
    }
    
    // 比根节点小,往左边找
    else if (root.val > key) {
        root.left = deleteNode(root.left, key)
    }
    
    // 找到了!
    else if (root.val == key) {
        // 情况1 和 情况 2
        if (root.left == nil) { return root.right }
        if (root.right == nil) { return root.left }
        
        // 情况 3
        // 找到最小的节点
        let minNode = getMinNode(root.right!)
        
        // 替换值
        root.val = minNode.val
        
        // 删除 子树中的最小的节点
        root.right = deleteNode(root.right, minNode.val)
    }
    return root
}

// 查找最小的节点
func getMinNode(_ root: TreeNode) -> TreeNode {
    var node = root
    while (node.left != nil) {
        node = node.left!
    }
    return node
}

0x03 我的作品

欢迎体验我的作品之一:小五笔
五笔学习好帮手!
App Store 搜索即可~


  • 1
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 打赏
    打赏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

豪冷啊

你的鼓励是对我的认可!

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值