Function decorator that caches function results

Lasse Vågsæther Karlsen lasse at vkarlsen.no
Sat Oct 8 11:32:16 EDT 2005


Lasse Vågsæther Karlsen wrote:
> Sam Pointon wrote:
> 
>> What about not storing args at all? Something like this:
<snip>

Ok, here's my updated version:

class cache(object):
     def __init__(self, timeout=0):
         self.timeout = timeout
         self.cache = {}

     def __call__(self, fn):
         arg_names = inspect.getargspec(fn)[0]
         def cached_result(*args, **kwargs):
             # Update named arguments with positional argument values
             kwargs.update(dict(zip(arg_names, args)))

             # Work out key as a tuple of ('argname', value) pairs
             key = tuple(sorted(kwargs.items()))

             # Check cache and return cached value if possible
             if key in self.cache:
                 (value, last_time) = self.cache[key]
                 if self.timeout <= 0 or time.time() - last_time <= 
self.timeout:
                     return value

             # Work out new value, cache it and return it
             result = fn(**kwargs)

             self.cache[key] = (result, time.time())
             return result

         # Return wrapper function
         return cached_result

Changed from previous versions:
- converted to class, must use () on decorator now
- added timeout, results will be recalculated when it expires
- timeout=0 means no timeout, results will always be reused
- now handles both positional and keyword arguments

-- 
Lasse Vågsæther Karlsen
http://usinglvkblog.blogspot.com/
mailto:lasse at vkarlsen.no
PGP KeyID: 0x2A42A1C2



More information about the Python-list mailing list