1. ホーム
  2. python

[解決済み] Pythonの条件付きwith文

2023-01-10 23:30:53

質問

コードのブロックをwith文で始める方法はありますか?ただし、条件付きで。

のようなものです。

if needs_with():
    with get_stuff() as gs:

# do nearly the same large block of stuff,
# involving gs or not, depending on needs_with()

明確にするために、あるシナリオではブロックが with 文に包まれており、別の可能性では同じブロックが包まれていない(すなわち、インデントされていないように)ことになります。

もちろん、初期の実験ではインデント エラーが発生します...。

どのように解決するのですか?

コードの重複を避けたい場合、Pythonの3.7より前のバージョンを使っている場合(その時 contextlib.nullcontext が導入された)、あるいは 3.3 よりも前のバージョンの Python を使っている場合。 contextlib.ExitStack が導入されたとき)、次のようなことができます。

class dummy_context_mgr():
    def __enter__(self):
        return None
    def __exit__(self, exc_type, exc_value, traceback):
        return False

または

import contextlib

@contextlib.contextmanager
def dummy_context_mgr():
    yield None

として使用します。

with get_stuff() if needs_with() else dummy_context_mgr() as gs:
   # do stuff involving gs or not

あるいは get_stuff() に基づいて異なるものを返すようにすることもできます。 needs_with() .

(参照 マイクの回答 または ダニエルの答え をご覧ください)。