Upgrade to Pro — share decks privately, control downloads, hide ads and more …

Context Managers

Context Managers

A quick look at python context managers -- a short talk given at the Memphis Python User Group (March 2016). http://mempy.org

Brad Montgomery

March 22, 2016
Tweet

More Decks by Brad Montgomery

Other Decks in Programming

Transcript

  1. # Opening a file # (handles opening and closing cleanly)

    with open('example.txt') as f: print(f.read()) SOME EXAMPLES…
  2. # Ensuring DB queries are atomic # (e.g. with Django's

    ORM) from django.db import transaction with transaction.atomic(): user = User.objects.create(...) user.profile.update(...) user.profile.save() SOME EXAMPLES…
  3. class Timed(): def __enter__(self): self.start = time() def __exit__(self, type,

    value, traceback): self.end = time() with Timed(): print("sleeping for 2...") sleep(2) BUILD YOUR OWN!
  4. from contextlib import contextmanager @contextmanager def timed(): start = time()

    yield end = time() with timed(): print("sleeping for 2...") sleep(2) BUILD YOUR OWN!
  5. from contextlib import contextmanager @contextmanager def timed(): start = time()

    yield end = time() with timed(): print("sleeping for 2...") sleep(2) assert(False) # fails... WHOOPS, EXCEPTIONS
  6. from contextlib import contextmanager @contextmanager def robust_timed(): start = time()

    try: yield finally: end = time() with robust_timed(): print("sleeping for 2...") sleep(2) assert(False) # the timer finishes WHOOPS, EXCEPTIONS
  7. def __exit__(self, type, value, traceback): # This code is guaranteed

    to run print("type: {}".format(type)) print("value: {}".format(value)) print("traceback: {}".format(traceback)) self.end = time() total = self.end - self.start print(“End: {} (total: {})”.format( self.end, total)) with Timed(): print("sleeping for 2...") sleep(2) assert(False) # Timed will finish WHOOPS, EXCEPTIONS
  8. with Timed() as timer: print("sleeping for 2...") sleep(2) t =

    time() + timer.start() print("started {}s ago".format(t) sleep(2) SUPPORT FOR as
  9. with Timed() as timer: print("sleeping for 2...") sleep(2) t =

    time() - timer.start print("started {}s ago".format(t)) sleep(2) # within the Timed class def __enter__(self): self.start = time() return self SUPPORT FOR as
  10. from contextlib import ContextDecorator # Using the ContextDecorator allows us

    to use # this as a decorator, too! class bettertimed(ContextDecorator): def __enter__(self): self.start = time() return self def __exit__(self, type, value, traceback): self.end = time() total = self.end - self.start THE CONTEXT DECORATOR CLASS
  11. with bettertimed(): sleep(1) print("ok... ") sleep(1) @bettertimed() def slow_print(text): sleep(1)

    print(text) sleep(1) slow_print('oh bother') THE CONTEXT DECORATOR CLASS