From 54700f2c8f0fd75b30b7468d9fea64cdea326b4d Mon Sep 17 00:00:00 2001 From: Pablo Date: Sat, 28 Oct 2017 16:17:55 -0300 Subject: [PATCH 1/3] Added delete function --- .../Binary Tree/binary_search_tree.py | 69 ++++++++++++++----- 1 file changed, 52 insertions(+), 17 deletions(-) diff --git a/data_structures/Binary Tree/binary_search_tree.py b/data_structures/Binary Tree/binary_search_tree.py index 2993c3cdc..c38751ad3 100644 --- a/data_structures/Binary Tree/binary_search_tree.py +++ b/data_structures/Binary Tree/binary_search_tree.py @@ -1,13 +1,14 @@ ''' A binary search Tree ''' - class Node: - def __init__(self, label): + def __init__(self, label, parent): self.label = label self.left = None self.right = None + #Added in order to delete a node easier + self.parent = parent def getLabel(self): return self.label @@ -27,6 +28,11 @@ class Node: def setRight(self, right): self.right = right + def getParent(self): + return self.parent + + def setParent(self, parent): + self.parent = parent class BinarySearchTree: @@ -35,13 +41,12 @@ class BinarySearchTree: def insert(self, label): # Create a new Node - new_node = Node(label) + new_node = Node(label, None) # If Tree is empty if self.empty(): self.root = new_node else: #If Tree is not empty - parent_node = None curr_node = self.root #While we don't get to a leaf while curr_node is not None: @@ -58,8 +63,14 @@ class BinarySearchTree: if new_node.getLabel() < parent_node.getLabel(): parent_node.setLeft(new_node) else: - parent_node.setRight(new_node) - + parent_node.setRight(new_node) + #Set parent to the new node + new_node.setParent(parent_node) + ''' + def delete(self): + if (not self.empty()): + if() + ''' def getNode(self, label): curr_node = None #If the tree is not empty @@ -78,6 +89,24 @@ class BinarySearchTree: curr_node = curr_node.getRight() return curr_node + def getMax(self): + #We go deep on the right branch + curr_node = None + if(not self.empty()): + curr_node = self.getRoot() + while(curr_node.getRight() is not None): + curr_node = curr_node.getRight() + return curr_node + + def getMin(self): + #We go deep on the left branch + curr_node = None + if(not self.empty()): + curr_node = self.getRoot() + while(curr_node.getLeft() is not None): + curr_node = curr_node.getLeft() + return curr_node + def empty(self): if self.root is None: return True @@ -92,19 +121,19 @@ class BinarySearchTree: def getRoot(self): return self.root -''' -Example - 8 - / \ - 3 10 - / \ \ - 1 6 14 - / \ / - 4 7 13 -''' +def testBinarySearchTree(): + ''' + Example + 8 + / \ + 3 10 + / \ \ + 1 6 14 + / \ / + 4 7 13 + ''' -if __name__ == "__main__": t = BinarySearchTree() t.insert(8) t.insert(3) @@ -128,3 +157,9 @@ if __name__ == "__main__": else: print("The label -1 doesn't exist") + if(not t.empty()): + print("Max Value: ", t.getMax().getLabel()) + print("Min Value: ", t.getMin().getLabel()) + +if __name__ == "__main__": + testBinarySearchTree() From f766bb42166b874364f30f022db738110a3dc567 Mon Sep 17 00:00:00 2001 From: Pablo Date: Sat, 28 Oct 2017 16:18:21 -0300 Subject: [PATCH 2/3] Added delete function --- .../Binary Tree/binary_search_tree.py | 100 ++++++++++++++---- 1 file changed, 79 insertions(+), 21 deletions(-) diff --git a/data_structures/Binary Tree/binary_search_tree.py b/data_structures/Binary Tree/binary_search_tree.py index c38751ad3..41ba87436 100644 --- a/data_structures/Binary Tree/binary_search_tree.py +++ b/data_structures/Binary Tree/binary_search_tree.py @@ -66,11 +66,29 @@ class BinarySearchTree: parent_node.setRight(new_node) #Set parent to the new node new_node.setParent(parent_node) - ''' - def delete(self): + + def delete(self, label): if (not self.empty()): - if() - ''' + #Look for the node with that label + node = self.getNode(label) + #If the node exists + if(node is not None): + #If it has no children + if(node.getLeft() is None and node.getRight() is None): + self.__reassignNodes(node, None) + node = None + #Has only right children + elif(node.getLeft() is None and node.getRight() is not None): + self.__reassignNodes(node, node.getRight()) + #Has only left children + elif(node.getLeft() is not None and node.getRight() is None): + self.__reassignNodes(node, node.getLeft()) + #Has two children + else: + tmpNode = self.getMax(node.getLeft()) + self.delete(tmpNode.getLabel()) + self.__reassignNodes(node, tmpNode) + def getNode(self, label): curr_node = None #If the tree is not empty @@ -89,18 +107,23 @@ class BinarySearchTree: curr_node = curr_node.getRight() return curr_node - def getMax(self): - #We go deep on the right branch - curr_node = None - if(not self.empty()): + def getMax(self, root = None): + if(root is not None): + curr_node = root + else: + #We go deep on the right branch curr_node = self.getRoot() + if(not self.empty()): while(curr_node.getRight() is not None): curr_node = curr_node.getRight() return curr_node - def getMin(self): - #We go deep on the left branch - curr_node = None + def getMin(self, root = None): + if(root is not None): + curr_node = root + else: + #We go deep on the left branch + curr_node = self.getRoot() if(not self.empty()): curr_node = self.getRoot() while(curr_node.getLeft() is not None): @@ -121,29 +144,58 @@ class BinarySearchTree: def getRoot(self): return self.root + def __isRightChildren(self, node): + if(node == node.getParent().getRight()): + return True + return False + + def __reassignNodes(self,node, newChildren): + if(newChildren is not None): + newChildren.setParent(node.getParent()) + if(node.getParent() is not None): + #If it is the Right Children + if(self.__isRightChildren(node)):a + node.getParent().setRight(newChildren) + else: + #Else it is the left children + node.getParent().setLeft(newChildren) + else: + #It is the root of the tree + node.setLabel(newChildren.getLabel()) def testBinarySearchTree(): ''' Example - 8 - / \ - 3 10 - / \ \ - 1 6 14 - / \ / - 4 7 13 + 8 + / \ + 3 10 + / \ \ + 1 6 14 + / \ / + 4 7 13 ''' + ''' + Example After Deletion + 7 + / \ + 3 14 + / \ + 1 6 + / + 4 + ''' t = BinarySearchTree() t.insert(8) t.insert(3) - t.insert(1) + t.insert(10) t.insert(6) - t.insert(4) - t.insert(7) + t.insert(1) t.insert(10) t.insert(14) t.insert(13) + t.insert(4) + t.insert(7) t.preShow(t.getRoot()) @@ -160,6 +212,12 @@ def testBinarySearchTree(): if(not t.empty()): print("Max Value: ", t.getMax().getLabel()) print("Min Value: ", t.getMin().getLabel()) + + t.delete(13) + t.delete(10) + t.delete(8) + + t.preShow(t.getRoot()) if __name__ == "__main__": testBinarySearchTree() From 9d8824658af8c657e3cc07e8192765b10d76f4d4 Mon Sep 17 00:00:00 2001 From: Pablo Date: Sat, 28 Oct 2017 18:33:14 -0300 Subject: [PATCH 3/3] Finished delete function and added some prints functions too --- .../Binary Tree/binary_search_tree.py | 70 ++++++++++++++----- 1 file changed, 52 insertions(+), 18 deletions(-) diff --git a/data_structures/Binary Tree/binary_search_tree.py b/data_structures/Binary Tree/binary_search_tree.py index 41ba87436..5290f685b 100644 --- a/data_structures/Binary Tree/binary_search_tree.py +++ b/data_structures/Binary Tree/binary_search_tree.py @@ -85,9 +85,12 @@ class BinarySearchTree: self.__reassignNodes(node, node.getLeft()) #Has two children else: + #Gets the max value of the left branch tmpNode = self.getMax(node.getLeft()) + #Deletes the tmpNode self.delete(tmpNode.getLabel()) - self.__reassignNodes(node, tmpNode) + #Assigns the value to the node to delete and keesp tree structure + node.setLabel(tmpNode.getLabel()) def getNode(self, label): curr_node = None @@ -135,11 +138,13 @@ class BinarySearchTree: return True return False - def preShow(self, curr_node): + def __InOrderTraversal(self, curr_node): + nodeList = [] if curr_node is not None: - print(curr_node.getLabel()) - self.preShow(curr_node.getLeft()) - self.preShow(curr_node.getRight()) + nodeList.insert(0, curr_node) + nodeList = nodeList + self.__InOrderTraversal(curr_node.getLeft()) + nodeList = nodeList + self.__InOrderTraversal(curr_node.getRight()) + return nodeList def getRoot(self): return self.root @@ -149,19 +154,44 @@ class BinarySearchTree: return True return False - def __reassignNodes(self,node, newChildren): + def __reassignNodes(self, node, newChildren): if(newChildren is not None): newChildren.setParent(node.getParent()) if(node.getParent() is not None): #If it is the Right Children - if(self.__isRightChildren(node)):a - node.getParent().setRight(newChildren) + if(self.__isRightChildren(node)): + node.getParent().setRight(newChildren) else: #Else it is the left children node.getParent().setLeft(newChildren) + + #This function traversal the tree. By default it returns an + #In order traversal list. You can pass a function to traversal + #The tree as needed by client code + def traversalTree(self, traversalFunction = None, root = None): + if(traversalFunction is None): + #Returns a list of nodes in preOrder by default + return self.__InOrderTraversal(self.root) else: - #It is the root of the tree - node.setLabel(newChildren.getLabel()) + #Returns a list of nodes in the order that the users wants to + return traversalFunction(self.root) + + #Returns an string of all the nodes labels in the list + #In Order Traversal + def __str__(self): + list = self.__InOrderTraversal(self.root) + str = "" + for x in list: + str = str + " " + x.getLabel().__str__() + return str + +def InPreOrder(curr_node): + nodeList = [] + if curr_node is not None: + nodeList = nodeList + InPreOrder(curr_node.getLeft()) + nodeList.insert(0, curr_node.getLabel()) + nodeList = nodeList + InPreOrder(curr_node.getRight()) + return nodeList def testBinarySearchTree(): ''' @@ -179,16 +209,12 @@ def testBinarySearchTree(): Example After Deletion 7 / \ - 3 14 - / \ - 1 6 - / - 4 + 1 4 + ''' t = BinarySearchTree() t.insert(8) t.insert(3) - t.insert(10) t.insert(6) t.insert(1) t.insert(10) @@ -197,7 +223,8 @@ def testBinarySearchTree(): t.insert(4) t.insert(7) - t.preShow(t.getRoot()) + #Prints all the elements of the list in order traversal + print(t.__str__()) if(t.getNode(6) is not None): print("The label 6 exists") @@ -216,8 +243,15 @@ def testBinarySearchTree(): t.delete(13) t.delete(10) t.delete(8) + t.delete(3) + t.delete(6) + t.delete(14) - t.preShow(t.getRoot()) + #Gets all the elements of the tree In pre order + #And it prints them + list = t.traversalTree(InPreOrder, t.root) + for x in list: + print(x) if __name__ == "__main__": testBinarySearchTree()