passing self data into a recursive function
I'm trying to set a function to do something like this
def __binaryTreeInsert(self, toInsert, currentNode=getRoot(), parentNode=None):
where current node starts as root, and then we change it开发者_JS百科 to a different node in the method and recursivly call it again.
However, i cannot get the 'currentNode=getRoot()' to work. If i try calling the funcion getRoot() (as above) it says im not giving it all the required variables, but if i try to call self.getRoot() it complains that self is an undefined variable. Is there a way i can do this without having to specify the root while calling this method?
EDIT: The base case of this method is already
if currentNode == None:
so using that to set the root wouldn't work
While arg=None
is the idiomatic Python sentinel value for an non-supplied argument, it doesn't have to be None
. In Lua, for instance, the idiomatic non-supplied argument is an empty table. We can actually apply that to this case:
class Foo:
sentinel = {}
def bar(self, arg=sentinel):
if arg is self.sentinel:
print "You didn't supply an argument!"
else:
print "The argument was", arg
f = Foo()
f.bar(123)
f.bar()
f.bar(None)
f.bar({})
Output:
The argument was 123 You didn't supply an argument! The argument was None The argument was {}
This works for any case except explicitly passing Foo.sentinel
, because Foo.sentinel
is guaranteed to have a unique address -- meaning, x is Foo.sentinel
is only true when x is Foo.sentinel
:) Thus, due to the closure we've created around Foo.sentinel
, there is only one object that can create an ambiguous situation, and it will never be used by accident.
You can do
def __binaryTreeInsert(self, toInsert, currentNode=None, parentNode=None):
if currentNode is None:
currentNode = self.getRoot()
...
When a function or method is defined, the def
line is evaluated immediately, including any keyword arguments. For this reason, things like function calls and mutable objects are usually not appropriate for default arguments.
The solution is instead to use a sentinel value. None
is most common, but for the cases that None
would be a valid value, you can use another sentinel, for example:
not_provided = object()
def _binaryTreeInsert(self, toInsert, currentNode=not_provided, parentNode=None):
if currentNode is not_provided:
currentNode = self.getRoot()
def __binaryTreeInsert(self, toInsert, currentNode=0, parentNode=None):
if not currentNode:
currentNode = self.getRoot()
精彩评论