我正在学习Python 3中的算法和数据结构课程,我的讲师最近向我们介绍了二叉搜索树。但是,我无法理解删除算法。下面是我们所教授的实现,但是当我最初写自己的演绎时,我没有包含“基础案例”,它仍然有效:
def remove(self, data):
if self.root:
self.root = self.remove_node(data, self.root)
def remove_node(self, data, node):
if node is None:
return node
if data < node.data:
node.leftChild = self.remove_node(data, node.leftChild)
elif data > node.data:
node.rightChild = self.remove_node(data, node.rightChild)
else:
if not node.rightChild and not node.leftChild:
print('removing leaf node')
del node
return None
if not node.leftChild:
print('removing node with single right child')
tempNode = node.rightChild
del node
return tempNode
elif not node.rightChild:
print('removing node with single left child')
tempNode = node.leftChild
del node
return tempNode
print('removing node with two children')
tempNode = self.get_predecessor(node.leftChild)
node.data = tempNode.data
node.leftChild = self.remove_node(tempNode.data, node.leftChild)
return node
现在,除了以下声明之外,所有这些对我都有意义:
if node is None:
return node
当我们之前了解基本情况时,我们被告知它们本质上是我们算法的出口点。但是,我不明白给定代码中的情况如何。首先,我没有看到节点是如何变空的,即使它是,为什么我们会返回一个空节点?据我所知,这个检查在整体递归中没有用处,因为我们似乎没有像任何其他递归函数那样“重复”。我非常感谢你的解释!
答案 0 :(得分:2)
基本情况通常用于一个或多个目的,包括;
删除树时,第一点并不是真正的问题(因为递归树只有有限数量的节点 - 与你递归的树相同)。您将关注第2点和第3点。
在你的功能中,你做有一个基本案例 - 事实上,你有两个(感谢@ user2357112) -
由
指定的未找到值的部分if node is None:
return node
和
由else
语句中的代码指定的值找到部分,用于执行实际删除。
为了使行为与递归案例保持一致,value-not-found基本案例返回None
。如您所见,第一个基本案例是一致执行上面概述的通用基本案例的第二个功能,而第二个基本案例执行第三个。