This is what I\'ve got so far but it is not working:
class Node:
rChild,lChild,data = None,None,None
def __init__(self,key):
self.rChild = N
The Op's Tree.insert
method qualifies for the "Gross Misnomer of the Week" award -- it doesn't insert anything. It creates a node which is not attached to any other node (not that there are any nodes to attach it to) and then the created node is trashed when the method returns.
For the edification of @Hugh Bothwell:
>>> class Foo(object):
... bar = None
...
>>> a = Foo()
>>> b = Foo()
>>> a.bar
>>> a.bar = 42
>>> b.bar
>>> b.bar = 666
>>> a.bar
42
>>> b.bar
666
>>>
The accepted answer neglects to set a parent attribute for each node inserted, without which one cannot implement a successor
method which finds the successor in an in-order tree walk in O(h) time, where h is the height of the tree (as opposed to the O(n) time needed for the walk).
Here is an implementation based on the pseudocode given in Cormen et al., Introduction to Algorithms, including assignment of a parent
attribute and a successor
method:
class Node(object):
def __init__(self, key):
self.key = key
self.left = None
self.right = None
self.parent = None
class Tree(object):
def __init__(self, root=None):
self.root = root
def insert(self, z):
y = None
x = self.root
while x is not None:
y = x
if z.key < x.key:
x = x.left
else:
x = x.right
z.parent = y
if y is None:
self.root = z # Tree was empty
elif z.key < y.key:
y.left = z
else:
y.right = z
@staticmethod
def minimum(x):
while x.left is not None:
x = x.left
return x
@staticmethod
def successor(x):
if x.right is not None:
return Tree.minimum(x.right)
y = x.parent
while y is not None and x == y.right:
x = y
y = y.parent
return y
Here are some tests to show that the tree behaves as expected for the example given by DTing:
import pytest
@pytest.fixture
def tree():
t = Tree()
t.insert(Node(3))
t.insert(Node(1))
t.insert(Node(7))
t.insert(Node(5))
return t
def test_tree_insert(tree):
assert tree.root.key == 3
assert tree.root.left.key == 1
assert tree.root.right.key == 7
assert tree.root.right.left.key == 5
def test_tree_successor(tree):
assert Tree.successor(tree.root.left).key == 3
assert Tree.successor(tree.root.right.left).key == 7
if __name__ == "__main__":
pytest.main([__file__])
I find the solutions a bit clumsy on the insert
part. You could return the root
reference and simplify it a bit:
def binary_insert(root, node):
if root is None:
return node
if root.data > node.data:
root.l_child = binary_insert(root.l_child, node)
else:
root.r_child = binary_insert(root.r_child, node)
return root
def BinaryST(list1,key):
start = 0
end = len(list1)
print("Length of List: ",end)
for i in range(end):
for j in range(0, end-i-1):
if(list1[j] > list1[j+1]):
temp = list1[j]
list1[j] = list1[j+1]
list1[j+1] = temp
print("Order List: ",list1)
mid = int((start+end)/2)
print("Mid Index: ",mid)
if(key == list1[mid]):
print(key," is on ",mid," Index")
elif(key > list1[mid]):
for rindex in range(mid+1,end):
if(key == list1[rindex]):
print(key," is on ",rindex," Index")
break
elif(rindex == end-1):
print("Given key: ",key," is not in List")
break
else:
continue
elif(key < list1[mid]):
for lindex in range(0,mid):
if(key == list1[lindex]):
print(key," is on ",lindex," Index")
break
elif(lindex == mid-1):
print("Given key: ",key," is not in List")
break
else:
continue
size = int(input("Enter Size of List: "))
list1 = []
for e in range(size):
ele = int(input("Enter Element in List: "))
list1.append(ele)
key = int(input("\nEnter Key for Search: "))
print("\nUnorder List: ",list1)
BinaryST(list1,key)
The problem, or at least one problem with your code is here:-
def insert(self,node,someNumber):
if node is None:
node = Node(someNumber)
else:
if node.data > someNumber:
self.insert(node.rchild,someNumber)
else:
self.insert(node.rchild, someNumber)
return
You see the statement "if node.data > someNumber:" and the associated "else:" statement both have the same code after them. i.e you do the same thing whether the if statement is true or false.
I'd suggest you probably intended to do different things here, perhaps one of these should say self.insert(node.lchild, someNumber) ?
Another Python BST solution
class Node(object):
def __init__(self, value):
self.left_node = None
self.right_node = None
self.value = value
def __str__(self):
return "[%s, %s, %s]" % (self.left_node, self.value, self.right_node)
def insertValue(self, new_value):
"""
1. if current Node doesnt have value then assign to self
2. new_value lower than current Node's value then go left
2. new_value greater than current Node's value then go right
:return:
"""
if self.value:
if new_value < self.value:
# add to left
if self.left_node is None: # reached start add value to start
self.left_node = Node(new_value)
else:
self.left_node.insertValue(new_value) # search
elif new_value > self.value:
# add to right
if self.right_node is None: # reached end add value to end
self.right_node = Node(new_value)
else:
self.right_node.insertValue(new_value) # search
else:
self.value = new_value
def findValue(self, value_to_find):
"""
1. value_to_find is equal to current Node's value then found
2. if value_to_find is lower than Node's value then go to left
3. if value_to_find is greater than Node's value then go to right
"""
if value_to_find == self.value:
return "Found"
elif value_to_find < self.value and self.left_node:
return self.left_node.findValue(value_to_find)
elif value_to_find > self.value and self.right_node:
return self.right_node.findValue(value_to_find)
return "Not Found"
def printTree(self):
"""
Nodes will be in sequence
1. Print LHS items
2. Print value of node
3. Print RHS items
"""
if self.left_node:
self.left_node.printTree()
print(self.value),
if self.right_node:
self.right_node.printTree()
def isEmpty(self):
return self.left_node == self.right_node == self.value == None
def main():
root_node = Node(12)
root_node.insertValue(6)
root_node.insertValue(3)
root_node.insertValue(7)
# should return 3 6 7 12
root_node.printTree()
# should return found
root_node.findValue(7)
# should return found
root_node.findValue(3)
# should return Not found
root_node.findValue(24)
if __name__ == '__main__':
main()