我不知道为什么我的程序不起作用,我认为我已经解决了所有情况,但没有删除任何东西,当我打印树时,有些东西正在移动。我认为插入功能的所有功能都正常,因为我没有遇到任何问题,但我无法成功删除。以下是两个功能:
def insert (self, x):
def recurse (p):
if x<p.data:
if p.left==None:
p.left = BSTNode (x)
else:
recurse (p.left)
else:
if p.right==None:
p.right = BSTNode (x)
else:
recurse (p.right)
# body of insert method
if self.root==None:
self.root = BSTNode(x)
else:
recurse (self.root)
这是插入,现在这里是删除:
def remove (self, x):
def recurse(p,x):
if x is p.data:
#if p is a leaf node then prune node p from tree
if p.left is None and p.right is None:
del p
# if p has a left child but no right child
elif p.left is not None and p.right is None:
p = p.left
#have to move up p.left now
#if p has a right child but no left child
elif p.right is not None and p.left is None:
p = p.right
#have to move up p.right now
#if p has a right child and a left child
elif p.right is not None and p.left is not None:
q = p
while True:
if q.data > p.data:
p.data = q.data
break
else:
if q.right is not None:
q = q.right
elif q.left is not None:
q = q.left
else:
q = p
break
if q is p:
while True:
if q.data > p.data:
p.data = q.data
break
else:
if q.left is not None:
q = q.left
if q.right is not None and q.right.data > p.data:
q = q.right
p.data = q.data
break
elif q.right is not None:
q = q.right
recurse(q,q.data)
elif x < p.data:
recurse(p.left,x)
elif x > p.data:
recurse(p.right,x)
if self.root is None:
print('there are no values left')
else:
recurse(self.root,x)
我的问题可能过于复杂,但这里的x是我想要移除的元素。 p是self.root树,q是删除后将替换p的节点,如果p有2个子节点。 q按照顺序遍历在下一行中选择。我必须为我的任务使用递归辅助函数。
答案 0 :(得分:0)
这是我的递归节点删除解决方案。它似乎运作正常:
(请查看我的完整RBTree来源和测试here)
class BlackNone(object):
'''
Represents None but with False is_red attribute.
Introduced to fix 'p.nodes[dir].is_red' problems with None node
'''
# ...
L, R = 0, 1 # Left & right directions
BNone = BlackNone() # None with False is_red attribute
class RBTree(object):
'''
My attempt to implement Red Black Tree.
Implementation follows this great tutorial:
http://www.eternallyconfuzzled.com/tuts/datastructures/jsw_tut_rbtree.aspx
'''
# ...
# RBTree methods:
def remove_recursive(self, root, data, done):
if not root:
done.append(False)
else:
if root.data == data:
if BNone in root.nodes:
save = root.nodes[not root.nodes[L]]
# case 0:
if root.is_red:
done.append(True)
elif save.is_red:
save.is_red = False
done.append(True)
root = BNone # actual node deletion
return save
else:
heir = root.nodes[L]
while heir.nodes[R]:
heir = heir.nodes[R]
root.data = heir.data
data = heir.data
dir = root.data < data
root.nodes[dir] = self.remove_recursive(root.nodes[dir],
data, done)
if not done:
root = self.remove_balance(root, dir, done)
return root
def remove(self, data):
done = []
self.root = self.remove_recursive(self.root, data, done)
if self.root:
self.root.is_red = False
return done.pop()
def remove_balance(self, root, dir, done):
p = root
s = root.nodes[not dir]
if s and (not s.is_red):
# Black sibling cases
if (not s.nodes[L].is_red) and (not s.nodes[R].is_red):
if p.is_red:
done.append(True)
p.is_red = True
s.is_red = True
else:
save = root.is_red;
p = self.rot_1(p, dir) if s.nodes[not dir].is_red else (
self.rot_2(p, dir))
p.is_red = save
p.nodes[L].is_red = False
p.nodes[R].is_red = False
done.append(True)
elif s and s.nodes[dir]:
# Red sibling cases
r = s.nodes[dir]
if (not r.nodes[L].is_red) and (not r.nodes[R].is_red):
p = self.rot_1(p, dir)
p.nodes[dir].nodes[not dir].is_red = True
else:
if r.nodes[dir].is_red:
s.nodes[dir] = self.rot_1(r, not dir)
p = self.rot_2(p, dir)
s.nodes[dir].is_red = False
p.nodes[not dir].is_red = True
p.is_red = False
p.nodes[dir].is_red = False
done.append(True)
return p
class RBNode(object):
'''
Red Black tree's node
'''