Python:with 文と contextmanager で try/finally を除外する

用途によってはクラスを作るより contextmanager の方がスッキリ書けると知ったのでメモです。
例えば、リソースを使う際に “開く/閉じる” や “接続/切断”、”確保/解放” などの処理を書くとき try/finally で囲みますが、そういったときに try/finally を contextmanager デコレータを付けた関数内で行い、使う側は with 文で書きます。

試すにあたって Google Colab を使いました。
そこにあった README.md を読み込んで表示してみました。
ファイルを例にサンプルを書きましたが、ファイルは次のように既に with 文で使えますので念のため。

with open('./sample_data/README.md', 'r') as f:
  print(f.read())

ということで、contextmanager を使って自作した場合は

from contextlib import contextmanager

@contextmanager
def sample_read(filename):
  file = open(filename, 'r')
  try:
    yield file
  finally:
    file.close()

with sample_read("./sample_data/README.md") as file:
  print(file.read())

contextmanager デコレータを付けた関数内で try/finally し、finally でファイルを閉じるようにしています。
ファイルのように with 文に対応しているものは良いですが、自前で解放が必要な場合は contextmanager でスッキリ書けそうです。

Docker Desktop for Windows/Macでつくるクリーンな開発環境構築入門(Python版) (Amazon)

コメント