Skip to content

Instantly share code, notes, and snippets.

@bofm
Last active March 5, 2018 19:42
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 bofm/548cec1f198d7e76560dafd479bf918c to your computer and use it in GitHub Desktop.
Save bofm/548cec1f198d7e76560dafd479bf918c to your computer and use it in GitHub Desktop.
Python deferred execution helper.
from collections import deque
from functools import partial, wraps
class Deferred:
"""
Deferred functions execution.
Usage:
>>> with Deferred() as deferred:
... for x in range(3):
... deferred.call(lambda x: x*2, x)
... results = list(deferred.results())
>>> results
[0, 2, 4]
>>> a = []
>>> with Deferred() as deferred:
... deferred.call(a.append, 1)
... deferred.run_all()
... assert a == [1]
... @deferred
... def append(x):
... a.append(x)
... append(2)
... assert a == [1]
>>> a
[1, 2]
"""
def __init__(self):
self._deferred = deque()
def __enter__(self):
return self
def __call__(self, fn):
@wraps(fn)
def wrapper(*args, **kwargs):
self.call(fn, *args, **kwargs)
return wrapper
def call(self, fn, *args, **kwargs):
self._deferred.append(partial(fn, *args, **kwargs))
def __exit__(self, exc_type, exc_val, exc_tb):
self.run_all()
def results(self):
while self._deferred:
yield self._deferred[0]()
self._deferred.popleft()
def run_all(self):
for _ in self.results():
pass
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment