1
1
'''
2
2
A binary search Tree
3
3
'''
4
-
5
4
class Node :
6
5
7
- def __init__ (self , label ):
6
+ def __init__ (self , label , parent ):
8
7
self .label = label
9
8
self .left = None
10
9
self .right = None
10
+ #Added in order to delete a node easier
11
+ self .parent = parent
11
12
12
13
def getLabel (self ):
13
14
return self .label
@@ -27,6 +28,11 @@ def getRight(self):
27
28
def setRight (self , right ):
28
29
self .right = right
29
30
31
+ def getParent (self ):
32
+ return self .parent
33
+
34
+ def setParent (self , parent ):
35
+ self .parent = parent
30
36
31
37
class BinarySearchTree :
32
38
@@ -35,13 +41,12 @@ def __init__(self):
35
41
36
42
def insert (self , label ):
37
43
# Create a new Node
38
- new_node = Node (label )
44
+ new_node = Node (label , None )
39
45
# If Tree is empty
40
46
if self .empty ():
41
47
self .root = new_node
42
48
else :
43
49
#If Tree is not empty
44
- parent_node = None
45
50
curr_node = self .root
46
51
#While we don't get to a leaf
47
52
while curr_node is not None :
@@ -58,7 +63,34 @@ def insert(self, label):
58
63
if new_node .getLabel () < parent_node .getLabel ():
59
64
parent_node .setLeft (new_node )
60
65
else :
61
- parent_node .setRight (new_node )
66
+ parent_node .setRight (new_node )
67
+ #Set parent to the new node
68
+ new_node .setParent (parent_node )
69
+
70
+ def delete (self , label ):
71
+ if (not self .empty ()):
72
+ #Look for the node with that label
73
+ node = self .getNode (label )
74
+ #If the node exists
75
+ if (node is not None ):
76
+ #If it has no children
77
+ if (node .getLeft () is None and node .getRight () is None ):
78
+ self .__reassignNodes (node , None )
79
+ node = None
80
+ #Has only right children
81
+ elif (node .getLeft () is None and node .getRight () is not None ):
82
+ self .__reassignNodes (node , node .getRight ())
83
+ #Has only left children
84
+ elif (node .getLeft () is not None and node .getRight () is None ):
85
+ self .__reassignNodes (node , node .getLeft ())
86
+ #Has two children
87
+ else :
88
+ #Gets the max value of the left branch
89
+ tmpNode = self .getMax (node .getLeft ())
90
+ #Deletes the tmpNode
91
+ self .delete (tmpNode .getLabel ())
92
+ #Assigns the value to the node to delete and keesp tree structure
93
+ node .setLabel (tmpNode .getLabel ())
62
94
63
95
def getNode (self , label ):
64
96
curr_node = None
@@ -78,45 +110,121 @@ def getNode(self, label):
78
110
curr_node = curr_node .getRight ()
79
111
return curr_node
80
112
113
+ def getMax (self , root = None ):
114
+ if (root is not None ):
115
+ curr_node = root
116
+ else :
117
+ #We go deep on the right branch
118
+ curr_node = self .getRoot ()
119
+ if (not self .empty ()):
120
+ while (curr_node .getRight () is not None ):
121
+ curr_node = curr_node .getRight ()
122
+ return curr_node
123
+
124
+ def getMin (self , root = None ):
125
+ if (root is not None ):
126
+ curr_node = root
127
+ else :
128
+ #We go deep on the left branch
129
+ curr_node = self .getRoot ()
130
+ if (not self .empty ()):
131
+ curr_node = self .getRoot ()
132
+ while (curr_node .getLeft () is not None ):
133
+ curr_node = curr_node .getLeft ()
134
+ return curr_node
135
+
81
136
def empty (self ):
82
137
if self .root is None :
83
138
return True
84
139
return False
85
140
86
- def preShow (self , curr_node ):
141
+ def __InOrderTraversal (self , curr_node ):
142
+ nodeList = []
87
143
if curr_node is not None :
88
- print (curr_node .getLabel ())
89
- self .preShow (curr_node .getLeft ())
90
- self .preShow (curr_node .getRight ())
144
+ nodeList .insert (0 , curr_node )
145
+ nodeList = nodeList + self .__InOrderTraversal (curr_node .getLeft ())
146
+ nodeList = nodeList + self .__InOrderTraversal (curr_node .getRight ())
147
+ return nodeList
91
148
92
149
def getRoot (self ):
93
150
return self .root
94
151
95
- '''
96
- Example
97
- 8
98
- / \
99
- 3 10
100
- / \ \
101
- 1 6 14
102
- / \ /
103
- 4 7 13
104
- '''
152
+ def __isRightChildren (self , node ):
153
+ if (node == node .getParent ().getRight ()):
154
+ return True
155
+ return False
105
156
157
+ def __reassignNodes (self , node , newChildren ):
158
+ if (newChildren is not None ):
159
+ newChildren .setParent (node .getParent ())
160
+ if (node .getParent () is not None ):
161
+ #If it is the Right Children
162
+ if (self .__isRightChildren (node )):
163
+ node .getParent ().setRight (newChildren )
164
+ else :
165
+ #Else it is the left children
166
+ node .getParent ().setLeft (newChildren )
106
167
107
- if __name__ == "__main__" :
168
+ #This function traversal the tree. By default it returns an
169
+ #In order traversal list. You can pass a function to traversal
170
+ #The tree as needed by client code
171
+ def traversalTree (self , traversalFunction = None , root = None ):
172
+ if (traversalFunction is None ):
173
+ #Returns a list of nodes in preOrder by default
174
+ return self .__InOrderTraversal (self .root )
175
+ else :
176
+ #Returns a list of nodes in the order that the users wants to
177
+ return traversalFunction (self .root )
178
+
179
+ #Returns an string of all the nodes labels in the list
180
+ #In Order Traversal
181
+ def __str__ (self ):
182
+ list = self .__InOrderTraversal (self .root )
183
+ str = ""
184
+ for x in list :
185
+ str = str + " " + x .getLabel ().__str__ ()
186
+ return str
187
+
188
+ def InPreOrder (curr_node ):
189
+ nodeList = []
190
+ if curr_node is not None :
191
+ nodeList = nodeList + InPreOrder (curr_node .getLeft ())
192
+ nodeList .insert (0 , curr_node .getLabel ())
193
+ nodeList = nodeList + InPreOrder (curr_node .getRight ())
194
+ return nodeList
195
+
196
+ def testBinarySearchTree ():
197
+ '''
198
+ Example
199
+ 8
200
+ / \
201
+ 3 10
202
+ / \ \
203
+ 1 6 14
204
+ / \ /
205
+ 4 7 13
206
+ '''
207
+
208
+ '''
209
+ Example After Deletion
210
+ 7
211
+ / \
212
+ 1 4
213
+
214
+ '''
108
215
t = BinarySearchTree ()
109
216
t .insert (8 )
110
217
t .insert (3 )
111
- t .insert (1 )
112
218
t .insert (6 )
113
- t .insert (4 )
114
- t .insert (7 )
219
+ t .insert (1 )
115
220
t .insert (10 )
116
221
t .insert (14 )
117
222
t .insert (13 )
223
+ t .insert (4 )
224
+ t .insert (7 )
118
225
119
- t .preShow (t .getRoot ())
226
+ #Prints all the elements of the list in order traversal
227
+ print (t .__str__ ())
120
228
121
229
if (t .getNode (6 ) is not None ):
122
230
print ("The label 6 exists" )
@@ -128,3 +236,22 @@ def getRoot(self):
128
236
else :
129
237
print ("The label -1 doesn't exist" )
130
238
239
+ if (not t .empty ()):
240
+ print ("Max Value: " , t .getMax ().getLabel ())
241
+ print ("Min Value: " , t .getMin ().getLabel ())
242
+
243
+ t .delete (13 )
244
+ t .delete (10 )
245
+ t .delete (8 )
246
+ t .delete (3 )
247
+ t .delete (6 )
248
+ t .delete (14 )
249
+
250
+ #Gets all the elements of the tree In pre order
251
+ #And it prints them
252
+ list = t .traversalTree (InPreOrder , t .root )
253
+ for x in list :
254
+ print (x )
255
+
256
+ if __name__ == "__main__" :
257
+ testBinarySearchTree ()
0 commit comments