Skip to content

Instantly share code, notes, and snippets.

@saulshanabrook
Last active August 29, 2015 14:04
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 saulshanabrook/e5000eebeffde91c7453 to your computer and use it in GitHub Desktop.
Save saulshanabrook/e5000eebeffde91c7453 to your computer and use it in GitHub Desktop.
$ python3 shelve_test.py
Opening handle
No cached results, calling function
outside function
Opening handle
Traceback (most recent call last):
File "shelve_test.py", line 46, in <module>
other_expensive_calculation()
File "shelve_test.py", line 29, in wrapper
_check_cache(c, key, user_function, args, kwds)
File "shelve_test.py", line 10, in _check_cache
result = func(*args, **kwargs)
File "shelve_test.py", line 44, in other_expensive_calculation
return expensive_calculation()
File "shelve_test.py", line 27, in wrapper
with shelve.open(filename, writeback=True) as c:
File "/usr/local/Cellar/python3/3.4.1/Frameworks/Python.framework/Versions/3.4/lib/python3.4/shelve.py", line 239, in open
return DbfilenameShelf(filename, flag, protocol, writeback)
File "/usr/local/Cellar/python3/3.4.1/Frameworks/Python.framework/Versions/3.4/lib/python3.4/shelve.py", line 223, in __init__
Shelf.__init__(self, dbm.open(filename, flag), protocol, writeback)
File "/usr/local/Cellar/python3/3.4.1/Frameworks/Python.framework/Versions/3.4/lib/python3.4/dbm/__init__.py", line 94, in open
return mod.open(file, flag, mode)
_gdbm.error: [Errno 35] Resource temporarily unavailable
import shelve
import functools
def _check_cache(cache_, key, func, args, kwargs):
if key in cache_:
print("Using cached results")
return cache_[key]
else:
print("No cached results, calling function")
result = func(*args, **kwargs)
cache_[key] = result
return result
def cache(filename):
def decorating_function(user_function):
def wrapper(*args, **kwds):
key = str(hash(functools._make_key(args, kwds, typed=False)))
handle_name = "{}_handle".format(filename)
if (hasattr(cache, handle_name) and
not hasattr(getattr(cache, handle_name).dict, "closed")
):
print("Using open handle")
return _check_cache(cache._handle, key,
user_function, args, kwds)
else:
print("Opening handle")
with shelve.open(filename, writeback=True) as c:
cache._handle = c # Save a reference to the open handle
_check_cache(c, key, user_function, args, kwds)
return functools.update_wrapper(wrapper, user_function)
return decorating_function
@cache(filename='cache')
def expensive_calculation():
print('inside function')
return
@cache(filename='cache')
def other_expensive_calculation():
print('outside function')
return expensive_calculation()
other_expensive_calculation()
print("Again")
other_expensive_calculation()
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment