Reputation: 803
I am trying to write a decorator function which converts a pure recursive function with two arguments that uses a "divide and conquer" strategy to an equivalent but more efficient one using dynamic programming. Note: it is designated to decorate two input functions.
So I am trying to memoize the values but I am not sure how to correctly implement it in the form of a decorator? Also how can it decorate two input functions?
EDIT: This is what I have managed to do:
profile_results = {}
t = {}
'''The profile function stores the following: the time taken by the function, the name of the function and the number of times it was called and stores these in the dictionary called *profile_results* '''
def profile(func):
import time
def wrapper(*args, **kwargs):
wrapper.calls += 1
name = func.__name__
t1 = time.time()
res = func(*args, **kwargs)
t2 = time.time() - t1
t = (t2)
my_tuple = (t,wrapper.calls)
profile_results[name] = my_tuple
return res
wrapper.calls = 0
return wrapper
#the dynamic function is the more efficient one and it is a decorator
@profile
def dynamic(func):
def wrapper(*args, **kwargs):
if args in t:
return t[args]
else:
res = func(*args, **kwargs)
t[args] = res
return res
return wrapper
#regular recursive function
@dynamic
@profile
def factorial(n):
if n == 0:
return 1
else:
return n * factorial(n-1)
This is what it prints out when I test it:
factorial(5)
print(t)
print (profile_results)
Output:
{(0,): 1, (1,): 1, (2,): 2, (3,): 6, (4,): 24, (5,): 120}
{'dynamic': (0.0, 1), 'factorial': (0.0, 6)}
The first output is correct but I am trying to profile it to see if the dynamic programming one is actually faster. However, it is showing the times as 0. Would I need to add a time.sleep() somewhere and where would I add it to correctly output the time (given that they are recursive functions)?
I am wondering if I am decorating it properly. I am trying to decorate the dynamic function which is a decorator as well. And I am trying to decorate the factorial function with both the dynamic and profile function.
Any help would be appreciated!
Upvotes: 1
Views: 369
Reputation: 1328
There's already a memoize / cache decorator in the standard library : https://docs.python.org/3/library/functools.html#functools.lru_cache
Don't re-invent the wheel, but perhaps it is not suited to what you need.
Upvotes: 1