与Python中的递归和属性设置器混淆
我正在尝试实现一个二进制搜索树类。我有两个班<代码>BSTNode和与Python中的递归和属性设置器混淆,python,recursion,binary-search-tree,Python,Recursion,Binary Search Tree,我正在尝试实现一个二进制搜索树类。我有两个班BSTNode和BST。我尝试在设置器中为left和right强制执行搜索树属性: class BSTNode(object): def __init__(self,new): if type(new) is BSTNode: self._data = new.data else: self._data = new self._left = No
BST
。我尝试在设置器中为left
和right
强制执行搜索树属性:
class BSTNode(object):
def __init__(self,new):
if type(new) is BSTNode:
self._data = new.data
else:
self._data = new
self._left = None
self._right = None
@property
def data(self):
return self._data
@property
def left(self):
return self._left
@left.setter
def left(self,data):
if data is None:
self._left = None
else:
n = BSTNode(data)
if n.data >= self.data:
del n
raise ValueError("Value must be less-than parent!")
self._left = n
@property
def right(self):
return self._right
@right.setter
def right(self,data):
if data is None:
self._right = None
else:
n = BSTNode(data)
if n.data < self.data:
del n
raise ValueError("Value must be greater-than or equal-to parent!")
self._right = n
class BST(object):
def __init__(self):
self._root = None
@property
def root(self):
return self._root
@root.setter
def root(self,value):
self._root = BSTNode(value)
def binary_insert(self,list_in):
self.root = binary_insert(list_in,0,len(list_in) - 1)
这是我的函数(注意上面类BST
中的实例方法binary\u insert
):
预期:
> t.root.left.data
0
> t.root.right.data
12
发生此问题的原因是,在完成所有递归并将根创建为BSTNode后,将执行以下行-
self.root = binary_insert(list_in,0,len(list_in) - 1)
也就是在末尾的binary\u insert()
返回一个BSTNode
作为根,它调用root
的setter
,这是-
@root.setter
def root(self,value):
self._root = BSTNode(value)
这会导致使用新的BSTNode
引用初始化self.\u root
,该引用的数据与从binary\u insert()
返回的root的数据相同,这将调用BSTNode的初始化()
,并将根作为参数传入。而BSTNode
的\uuuu init\uuu()
函数执行以下操作-
def __init__(self,new):
if type(new) is BSTNode:
self._data = new.data
else:
self._data = new
self._left = None
self._right = None
在这里,您将self.\u left
设置为None
并将self.\u right
设置为None
。正如您所观察到的,根的左值和右值都是零
有两种方法可以解决这个问题,一种是-
将要设置的self.root
行更改为-
def binary_insert(self,list_in):
self._root = binary_insert(list_in,0,len(list_in) - 1)
或者,您也可以更改\uu init\uuu()
BSTNode,这样,如果类型(新)
是BSTNode
,您也可以从新的BSTNode
复制左侧的和右侧的值。范例-
def __init__(self,new):
if type(new) is BSTNode:
self._data = new.data
self._left = new.left
self._right = new.right
else:
self._data = new
self._left = None
self._right = None
看起来您的insert方法正在构建一棵树,但它没有附加到根,并且对该树的所有引用都将丢失
顺便说一句,请注意,平衡树的方法(选择列表分区的中间部分)仅在列表已排序时有效。您需要事先对列表进行排序,或者使用更通用的平衡方案,如AVL树或红黑树您能澄清您的实际问题吗?输出的哪一部分是您不期望的,而您期望它是什么呢?好吧,现在看起来很明显!非常感谢。
def __init__(self,new):
if type(new) is BSTNode:
self._data = new.data
else:
self._data = new
self._left = None
self._right = None
def binary_insert(self,list_in):
self._root = binary_insert(list_in,0,len(list_in) - 1)
def __init__(self,new):
if type(new) is BSTNode:
self._data = new.data
self._left = new.left
self._right = new.right
else:
self._data = new
self._left = None
self._right = None