I tried to play with using a decorator on a recursive function such as the one that calculates the nth
Fibonacci number.
Below is the code I wrote:
class FibList:
# decorator will return a list of fibonacci numbers from 0 to n.
def __init__(self, func):
self.func = func
def __call__(self, *args):
return [self.func(x) for x in range(args[0])]
@FibList
def fibonacci(n):
# function will return nth fibonacci number
if n < 2:
return n
else:
return fibonacci(n-2) fibonacci(n-1)
if __name__ == "__main__":
a = fibonacci(4)
print(a)
The output for a
looks like this: [0, 1, [0], [0, 0, 1]]
. But, I am expecting the output looks like this: [0, 1, 1, 2]
I am really having a hard time understanding what is going on inside the decorated fibonacci
function.
If anyone can help me to clarify such strange behavior, I will be much appreciated it. Thank you.
CodePudding user response:
Your issue is caused by multiple recursion.
If you run the debugger and check each call of the recursive function, you will notice that the if-block returns the number correctly. That's why the first two numbers in your result list are correct.
But as soon as it reaches the else-block, it will call the __call__
method of the Class with n-2
and n-1
respectively and thus create a new sublist inside of your result list.
When `n==2` the result would become:
fibonacci(n-2) -> __call__(self, 0) --> []
fibonacci(n-1) -> __call__(self, 1) --> [0]
return fibonacci(n-2) fibonacci(n-1) --> [] [0] = [0]
For n==3
you would get the last sublist [0,0,1]
You need to find a way to prevent this multi-recursive call.