二叉搜索树(Binary Search Tree,简称BST)是一种特殊的二叉树,它具有以下性质:
// 二叉搜索树的节点
type BinarySearchTreeNode struct {
Value int // 值
Left *BinarySearchTreeNode // 左子树
Right *BinarySearchTreeNode // 右子树
}
// 二叉搜索树
type BinarySearchTree struct {
Root *BinarySearchTreeNode
}
// 实例化
func NewBinarySearchTree() *BinarySearchTree {
return &BinarySearchTree{}
}
// 二叉搜索树 插入节点
func (BST *BinarySearchTree) Insert(val int) {
// 定义一个递归函数 插入节点
var insertNode func(node *BinarySearchTreeNode, val int) *BinarySearchTreeNode
insertNode = func(node *BinarySearchTreeNode, val int) *BinarySearchTreeNode {
// 如果节点为空,则创建新节点
if node == nil {
return &BinarySearchTreeNode{Val: val}
}
// 如果值小于节点值,则插入到左子树
if val < node.Val {
node.Left = insertNode(node.Left, val)
} else if val > node.Val { // 如果值大于节点值,则插入到右子树
node.Right = insertNode(node.Right, val)
}
return node
}
// 调用递归函数插入节点 从根节点开始
BST.Root = insertNode(BST.Root, val)
}
// 二叉搜索树 查找
func (BST *BinarySearchTree) Find(val int) *BinarySearchTreeNode {
var findNode func(node *BinarySearchTreeNode, val int) *BinarySearchTreeNode
findNode = func(node *BinarySearchTreeNode, val int) *BinarySearchTreeNode {
if node == nil {
return nil
}
if node.Val == val {
return node
} else if val < node.Val {
return findNode(node.Left, val)
} else {
return findNode(node.Right, val)
}
}
return findNode(BST.Root, val)
}
// 二叉搜索树 删除
func (BST *BinarySearchTree) Delete(val int) {
var deleteNode func(node *BinarySearchTreeNode, val int) *BinarySearchTreeNode
deleteNode = func(node *BinarySearchTreeNode, val int) *BinarySearchTreeNode {
if node == nil {
return nil
}
if val < node.Val {
node.Left = deleteNode(node.Left, val)
} else if val > node.Val {
node.Right = deleteNode(node.Right, val)
} else {
// 有两个子节点 找到右子树的最小节点
if node.Left != nil && node.Right != nil {
var findMin func(node *BinarySearchTreeNode) *BinarySearchTreeNode
findMin = func(node *BinarySearchTreeNode) *BinarySearchTreeNode {
if node.Left == nil {
return node
}
return findMin(node.Left)
}
minNode := findMin(node.Right)
node.Val = minNode.Val
node.Right = deleteNode(node.Right, minNode.Val)
} else if node.Left != nil { // 只有一个左子节点
node = node.Left
} else if node.Right != nil { // 只有一个右子节点
node = node.Right
} else { // 没有子节点 直接删除
node = nil
}
}
return node
}
BST.Root = deleteNode(BST.Root, val)
}
查找、插入、删除:平均时间复杂度为 O(log n),但在最坏情况下(例如,插入有序数据导致树退化为链表),时间复杂度为 O(n)。
遍历操作:由于需要访问每个节点,时间复杂度为 O(n)。
为了克服普通二叉搜索树的缺点,计算机科学家们设计了多种平衡二叉树: