Skip to content

Instantly share code, notes, and snippets.

@gitex
Created June 1, 2016 16:38
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save gitex/2e0a078bf382aed17200bb4da4a7d8c3 to your computer and use it in GitHub Desktop.
Save gitex/2e0a078bf382aed17200bb4da4a7d8c3 to your computer and use it in GitHub Desktop.
Python: caching the values of functions at certain times
#!/usr/bin/env python
# -*- coding: utf-8 -*-
from datetime import timedelta, datetime
from time import sleep
from functools import partial
class Cache(object):
"""Class caching function's results for some time.
Using:
cache = Cache(max_time_default)
@cache
def some_function(*args, **kwargs)
return someone
Also, every function can save any max time. Call this function with argument "max_age":
some_function(args, kwargs, max_age=4)
"""
def __init__(self, max_time_default, *args, **kwargs):
self.cached_responses = {}
self.max_time_default = max_time_default if max_time_default else 0
def __call__(self, function):
def wrapped(*args, **kwargs):
max_time = kwargs.get('max_age', None)
if max_time:
del kwargs['max_age']
if not max_time:
max_time = self.max_time_default
if self.cached_responses.get(function, None):
last_added_time = self.cached_responses[function].get('datetime')
else:
last_added_time = None
if last_added_time and (datetime.now() - last_added_time).seconds > max_time or not last_added_time:
response = function(*args, **kwargs)
self.cached_responses[function] = {
'datetime': datetime.now(),
'response': response
}
return response
else:
return self.cached_responses[function]['response']
wrapped.__name__ = function.__name__
return wrapped
if __name__ == '__main__':
cache = Cache(max_time_default=2)
@cache # < --- Add decorator of cache for function
def func(a):
return a
print func(1) # Return 1: function not called earlier, will call
print func(2) # Return 1: cached value of function
sleep(5)
print func(3) # Return 3: cached value is old, will call again
sleep(5)
print func(4, max_age=10) # Return 3: max age was changed
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment