Reputation: 676
I have a BST in python, with each node holding 3 pieces of data. Those pieces of data being ID, Mark, and Name.
What I'm trying to do is search for a Name, but the nodes are based on IDs, this is how I've searched. The function is supposed to output the ID of the specific Name.
def findName(tree,name):
if tree==None:
return None
elif tree['name']==name:
return tree['id']
if tree['left']!=None:
return findName(tree['left'],name)
if tree['right']!=None:
return findName(tree['right'],name)
Unfortunately I'll only ever be searching the left side of the Tree, and not the right, the opposite applies if I search the right side first.
How do I search both sides for this?
Upvotes: 1
Views: 634
Reputation: 199
try this:
def search(node, name):
self_result = [node['id']] if node['name'] == name else []
if not node['left'] and not node['right']:
return self_result
elif node['left'] and not node['right']:
return self_result + search(node['left'], name)
elif not node['left'] and node['right']:
return self_result + search(node['right'], name)
else:
return self_result + search(node['left'], name) + search(node['right'], name)
test_tree = {'id':0, 'name': 'a',
'left': {'id':1, 'name': 'a',
'left':{'id':3, 'name':'c',
'left':{'id':4,'name': 'd',
'left' : None,
'right' : None},
'right':None},
'right':{'id':4, 'name':'e',
'left': None,
'right': None}
},
'right': {'id':5, 'name':'c',
'left': {'id':6, 'name':'e',
'left': None,
'right': None},
'right': {'id': 7, 'name': 'a',
'left' : {'id' : 8, 'name': 'b',
'left': None,
'right' : None},
'right' : None
}
}
}
if __name__ == '__main__':
assert search(test_tree, 'a') == [0, 1, 7]
assert search(test_tree, 'b') == [8]
assert search(test_tree, 'c') == [3, 5]
assert search(test_tree, 'e') == [4, 6]
print 'ok'
It can also deal with multiple matches.
Upvotes: 0
Reputation: 304137
You could traverse the branches like this if you wish to avoid the extra recursive call. Note that it is preferable to test identity of None
rather than equality
for branch in ('left', 'right'):
if tree[branch] is not None:
result = findName(tree[branch], name)
if result is not None:
return result
Upvotes: 0
Reputation: 86774
...
result = findName(tree['left'],name)
if result is None:
result = findName(tree['right'],name)
return result
Upvotes: 2
Reputation: 5706
The problem is you are returning in the
if tree['left']!=None:
return findName(tree['left'],name)
What you have to do is create a local variable and set it to the value from findName()
then if you get None continue with the right otherwise return the value.
Upvotes: 0
Reputation: 95298
You shouldn't return
if you're not yet finished! Instead, you can replace your last 4 lines with a single, short-circuiting or
:
return findName(tree['left'], name) or findName(tree['right'], name)
Make sure your IDs don't include 0
, though, otherwise this method will fail because 0
is a falsy value, just like None.
Upvotes: 5