抜粋翻訳 PEP 343: The "with" Statement

概要

このPEPは、try/finally文の標準的な使い方を切り出すことが可能なように、Python言語に新しい文 "with" を追加する。

このPEPの中で、「コンテキストマネージャ」はメソッド __enter__() および __exit__() を提供する。これはwith文に入る際と出る際に呼ばれるメソッドである。

導入

PEP 340とその代替案に関するたくさんの議論を経て、私は PEP 340 を撤回することに決めた。そして若干の変更を加えたものを PEP 310 で提案した。さらなる議論の末、throw()メソッドを使って停止中のジェネレータの中で例外を投げることの出来る機能と、そして新しい例外 GeneratorExit を投げる close() メソッドをを追加し直した。これらの追加は当初 python-dev [2] で提案され、全面的に賛同されたものである。また、キーワードをwithに変更した。

動機と要約

PEP 340, 無名ブロック文, はいくつものパワフルなアイデアを結びつけた。ジェネレータをブロックのテンプレートとして使う、ジェネレータに例外ハンドリングと終了処理を追加する、などである。一部の称賛を横目にたくさんの反対意見が出された。彼らは元々あった、だがはっきりとは見えていなかった、潜在的なループ構造が気に入らなかったのだ。つまり、ブロック文の中でのbreakやcontinueはそのブロック文をbreakしたりcontinueしたりする。たとえそれがループをしないリソース管理ツールとして使われていたとしても。

しかし、とどめは私がRaymond Chenのフロー制御マクロについての暴言[1]を読んだときに刺された。Raymondは確信を持ってマクロのなかにフロー制御を隠してしまうのはコードを理解不能にすると主張した。そして私は、彼の主張がCと同様にPythonにも適用できる、と気づいた。PEP 340のテンプレートはあらゆる種類の制御フローを隠すことが出来る。たとえば、PEP 340の例4 (auto_retry()) は例外をキャッチしブロックを3回まで繰り返す。

この点、PEP 310のwith文は、私の見解では制御フローを隠さない。finally節は一時的に制御フローを停止するだろうが、最終的には、finally節がまったくなかったのと同じ形に戻る。