[解決済み] Pythonでは'finally'は常に実行されるのですか?
質問
Python の任意の try-finally ブロックに対して
finally
ブロックは必ず実行されますか?
たとえば、私が
except
ブロックを作成します。
try:
1/0
except ZeroDivisionError:
return
finally:
print("Does this code run?")
をリレイズするとか。
Exception
:
try:
1/0
except ZeroDivisionError:
raise
finally:
print("What about this code?")
テストでは
finally
上記の例では実行されますが、私が思いつかないようなシナリオもあるかと思います。
を使用するシナリオはありますか?
finally
ブロックは Python で実行に失敗することがありますか?
解決方法は?
の実装よりもはるかに強力な言葉です。
finally
を提供します。保証されるのは、もし実行が全体の
try
-
finally
の構成では
finally
を実行します。保証されないのは、実行が
try
-
finally
.
-
A
finally
ジェネレータや非同期コルーチンでは、決して実行されないかもしれません。 もし、そのオブジェクトが最後まで実行されなかったら。このようなことが起こる可能性はたくさんありますが、ここではその一つを紹介します。def gen(text): try: for line in text: try: yield int(line) except: # Ignore blank lines - but catch too much! pass finally: print('Doing important cleanup') text = ['1', '', '2', '', '3'] if any(n > 1 for n in gen(text)): print('Found a number') print('Oops, no cleanup.')
この例は少しトリッキーであることに注意してください。ジェネレータがガベージコレクションされるとき、Pythonは
finally
を投げてブロック化します。GeneratorExit
の例外が発生しますが、ここではその例外をキャッチした上でyield
その時点で Python は警告 ("generator ignored GeneratorExit") を表示し、あきらめます。参照 PEP 342 (強化されたジェネレータによるコルーチン) をご覧ください。ジェネレータやコルーチンが結論まで実行されない他の方法としては、オブジェクトがGCされない場合(CPythonでも可能です)、あるいは
async with
await
の中の__aexit__
である場合、またはオブジェクトawait
またはyield
の中にあるfinally
ブロックを作成します。このリストは、すべてを網羅することを意図したものではありません。 -
A
finally
を実行しないかもしれません。 すべての非デーモンスレッドが先に終了した場合。 -
os._exit
は直ちに処理を停止します を実行することなくfinally
のブロックを作成します。 -
os.fork
が発生する可能性があります。finally
ブロックが 実行 2回 . 物事が2回起こることから予想される通常の問題だけでなく、共有リソースにアクセスできない場合、同時アクセスの競合(クラッシュ、ストール、...)を引き起こす可能性があります。 正しく同期させる .以来
multiprocessing
を使うときは、fork-without-exec を使ってワーカープロセスを作成します。 フォーク 開始メソッド (Unixのデフォルト)を呼び出し、次にos._exit
は、ワーカーの仕事が終わると、ワーカーの中でfinally
とmultiprocessing
の相互作用が問題になることがあります ( 例 ). -
Cレベルのセグメンテーションフォールトは、以下のことを防ぐことができます。
finally
ブロックが実行されなくなります。 -
kill -SIGKILL
を防ぐことができます。finally
ブロックが実行されないようにします。SIGTERM
とSIGHUP
はまたfinally
ブロックは、シャットダウンを制御するハンドラを自分でインストールしない限り、実行されません。SIGTERM
またはSIGHUP
. -
での例外
finally
は、クリーンアップの完了を妨げることがあります。特に注目すべきケースは、ユーザが control-C ちょうど を実行し始めたところでfinally
ブロックを作成します。PythonはKeyboardInterrupt
のすべての行をスキップします。finally
ブロックの内容を (KeyboardInterrupt
-安全なコードを書くのは非常に難しいです)。 -
コンピューターの電源が切れたり、ハイバネートして起きない場合。
finally
ブロックは実行されません。
は
finally
ブロックはトランザクションシステムではないので、アトミック性の保証やその種のものは提供しません。これらの例のいくつかは明白に思えるかもしれませんが、そのようなことが起こりうることを忘れがちで、そのような場合は
finally
を使うことが多いのです。
関連
-
Pythonの画像ファイル処理用ライブラリ「Pillow」(グラフィックの詳細)
-
[解決済み】Python regex AttributeError: 'NoneType' オブジェクトに 'group' 属性がない。
-
[解決済み] プログラムの実行やシステムコマンドの呼び出しはどのように行うのですか?
-
[解決済み] Pythonには文字列の'contains'サブストリングメソッドがありますか?
-
[解決済み] Pythonで現在時刻を取得する方法
-
[解決済み】if __name__ == "__main__": は何をするのでしょうか?
-
[解決済み】ネストされたディレクトリを安全に作成するには?
-
[解決済み】Javaではfinallyブロックは必ず実行されるのですか?
-
[解決済み】Pythonに三項条件演算子はありますか?
-
[解決済み】Pythonでtry-except-elseを使用するのは良い習慣ですか?
最新
-
nginxです。[emerg] 0.0.0.0:80 への bind() に失敗しました (98: アドレスは既に使用中です)
-
htmlページでギリシャ文字を使うには
-
ピュアhtml+cssでの要素読み込み効果
-
純粋なhtml + cssで五輪を実現するサンプルコード
-
ナビゲーションバー・ドロップダウンメニューのHTML+CSSサンプルコード
-
タイピング効果を実現するピュアhtml+css
-
htmlの選択ボックスのプレースホルダー作成に関する質問
-
html css3 伸縮しない 画像表示効果
-
トップナビゲーションバーメニュー作成用HTML+CSS
-
html+css 実装 サイバーパンク風ボタン
おすすめ
-
ピロウズ画像色処理の具体的な活用方法
-
pythonサイクルタスクスケジューリングツール スケジュール詳解
-
python implement mysql add delete check change サンプルコード
-
任意波形を生成してtxtで保存するためのPython実装
-
Python 入出力と高次代入の基礎知識
-
[解決済み】RuntimeWarning: invalid value encountered in double_scalars で numpy の除算ができない。
-
[解決済み】ilocが「IndexError: single positional indexer is out-of-bounds」を出す。
-
[解決済み】Pythonでgoogle APIのJSONコードを読み込むとエラーになる件
-
[解決済み】 AttributeError("'str' object has no attribute 'read'")
-
[解決済み】ImportError: bs4という名前のモジュールがない(BeautifulSoup)