Pythonの例外処理

例外と構文エラーを区別する##

Pythonプログラムの作成時にエラーが報告されることがよくあります。エラーは通常、次の2つの状況で報告されます。

  1. 構文エラー:一部の構文エラーは例外です
  2. 例外

文法上の誤り###

構文エラーは解析エラーとも呼ばれ、発生する最も一般的なタイプのエラーです。

In [1]:while True print('Hello!')
 File "<ipython-input-1-5c66e4fd0ae9>", line 1while True print('Hello!')^
SyntaxError: invalid syntax

コードがPython構文に準拠していない場合、SyntaxErrorがスローされます。

異常な###

Pythonは、例外オブジェクトを使用して異常な状況を表します。エラーが発生した後、例外が発生します。例外が処理またはキャッチされない場合、プログラムは** traceback **を使用してプログラムの実行を終了し、マルチスレッドプログラム内にある場合は、現在のスレッドの実行を終了します。

In [2]:1/0---------------------------------------------------------------------------
ZeroDivisionError                         Traceback(most recent call last)<ipython-input-2-05c9758a9c21>in<module>()---->11/0

ZeroDivisionError: division by zero

0で除算すると、ZeroDivisionError例外(ZeroDivisionErrorクラスのインスタンス)がスローされます。

例外階層##

Python3.5.2の組み込み例外のクラス階層は次のとおりです。標準ライブラリを参照してください

BaseException  #すべての例外の基本クラス
 +- - SystemExit  #プログラム終了/終了
 +- - KeyboardInterrupt  #キーボードによって中断されました(通常はCtrl+C)生む
 +- - GeneratorExit  #ジェネレーターによる.close()メソッドトリガー
 +- - Exception  #出口以外のすべての例外の基本クラス
  +- - StopIteration  #反復エラーの停止
  +- - StopAsyncIteration  #非同期反復エラーを停止します
  +- - ArithmeticError  #算術例外の基本クラス
  |+- - FloatingPointError  #フローティングポイント操作例外
  |+- - OverflowError  #オーバーフローによる例外
  |+- - ZeroDivisionError  #0の除算またはモジュロ演算によって引き起こされる例外
  +- - AssertionError  #assertステートメントによって発生します
  +- - AttributeError  #属性名が無効な場合に発生します
  +- - BufferError  #バッファエラーが発生しました
  +- - EOFError  #ファイルの終わりに達したときに発生します
  +- - ImportError  #インポートステートメントが失敗しました
  +- - LookupError  #インデックスとキーエラー
  |+- - IndexError  #シーケンスインデックスの範囲外
  |+- - KeyError  #キーが存在しません
  +- - MemoryError  #ストレージが足りない
  +- - NameError  #ローカル名またはグローバル名が見つかりません
  |+- - UnboundLocalError  #バインドされていないローカル変数
  +- - OSError  #オペレーティングシステムエラー
  |+- - BlockingIOError  #IOブロッキング
  |+- - ChildProcessError  #子プロセス
  |+- - ConnectionError  #接続エラー
  ||+- - BrokenPipeError  #パイプが切断されました
  ||+- - ConnectionAbortedError  #接続が中止されました
  ||+- - ConnectionRefusedError  #接続拒否
  ||+- - ConnectionResetError  #接続リセット
  |+- - FileExistsError #ファイルが既に存在します
  |+- - FileNotFoundError  #ファイルが存在しません
  |+- - InterruptedError  #割り込みエラー
  |+- - IsADirectoryError  #ディレクトリエラー
  |+- - NotADirectoryError  #ディレクトリ以外のエラー
  |+- - PermissionError  #許可エラー
  |+- - ProcessLookupError  #プロセスルックアップエラー
  |+- - TimeoutError  #タイムアウトエラー
  +- - ReferenceError  #参照されたオブジェクトが破棄された後も、参照は引き続き使用されます
  +- - RuntimeError  #ランタイムエラー
  |+- - NotImplementedError  #実装されていない機能
  |+- - RecursionError  #再帰エラー
  +- - SyntaxError  #文法上の誤り
  |+- - IndentationError  #インデントエラー
  |+- - TabError  #一貫性のないタブを使用する
  +- - SystemError  #インタープリターの致命的でないシステムエラー
  +- - TypeError  #間違ったタイプが操作に渡されました
  +- - ValueError  #タイプが無効です
  |+- - UnicodeError  #Unicodeエラー
  |+- - UnicodeDecodeError  #Unicodeデコードエラー
  |+- - UnicodeEncodeError  #Unicodeエンコーディングエラー
  |+- - UnicodeTranslateError  #Unicode変換エラー
  +- - Warning  #警告の基本クラス
   +- - DeprecationWarning  #非推奨の機能に関する警告
   +- - PendingDeprecationWarning  #廃止される機能に関する警告
   +- - RuntimeWarning  #疑わしいランタイム動作の警告
   +- - SyntaxWarning  #疑わしい構文の警告
   +- - UserWarning  #ユーザーコードによって生成された警告
   +- - FutureWarning  #将来のセマンティクスの構造変更に関する警告
   +- - ImportWarning  #インポートステートメントの警告
   +- - UnicodeWarning  #Unicode警告
   +- - BytesWarning  #バイト警告
   +- - ResourceWarning  #リソースの警告

例外をキャッチ##

try / exceptステートメントを使用して例外をキャッチできます。 try / exceptionステートメントは、tryステートメントブロック内のエラーを検出するために使用されるため、exceptステートメントは例外情報をキャプチャして処理します。

try/except

基本的な文法

try:<ステートメント>
except <name>:
 < ステートメント>          #tryセクションで呼び出された場合'name'例外、このコードを実行します

In [3]:try:...:     x =int(input("Please enter a number: "))...: except ValueError:...:print("No valid number.")...:     
Please enter a number: asd
No valid number.

###を除く複数

In [4]:import sys

In [5]:try:...:     f =open('file.txt')  #ファイルが存在しない場合、FileNotFoundErrorがスローされます
 ...:  s = f.readline()...:     i =int(s.strip())...: except OSError:  #FileNotFoundErrorの上位層の例外
 ...: print('OS error.')...: except ValueError:...:print('Could not convert data to integer.')...: except Exception:...:print('Exception.')...: except:  #特定の例外タイプが追加されていない場合、すべての例外がキャッチされるため、使用または注意して使用しないでください。
 ...: print('Unexpected error:', sys.exc_info()[0])...:     
OS error.

以下を除く各間の実行の順序:

オプションのelseステートメント###

文法

try:<ステートメント>
except <name>:
 < ステートメント>          #tryセクションで呼び出された場合'name'例外、このコードを実行します
else:<ステートメント>          #例外が発生しない場合は、このコードを実行します

try部分が例外をスローしないが、実行する必要のあるステートメントがelseステートメントに配置されている場合。

コード

for arg in sys.argv[1:]:try:
  f =open(arg,'r')
 except IOError:print('cannot open', arg)else:  #例外がスローされない場合(つまり、ファイルが正しく開かれている場合)、ファイルのすべての行を出力します。
  print(arg,'has',len(f.readlines()),'lines')
  f.close()

最後にステートメント###

finalステートメントは、どのような状況でも実行する必要のあるステートメントを定義するために使用されます。

In [1]:try:...:     raise KeyboardInterrupt
 ...: finally:...:print('Goodbye')...:     
Goodbye
---------------------------------------------------------------------------
KeyboardInterrupt                         Traceback(most recent call last)<ipython-input-8-132d568ca0fb>in<module>()1try:---->2     raise KeyboardInterrupt
  3 finally:4print('Goodbye')5 

KeyboardInterrupt:

リターンステートメントを使用した最終実行順序

def p(x):print(x)return x

def t():try:returnp(2)print('haha')finally:returnp(3)

x =t()

# 出力は次のとおりです。
23
# 戻り値xは3です

tryブロックでは、finallyステートメントがある限り、関数が早く戻っても、tryブロックを終了する前にfinallyステートメントが実行されるため、finallyでは戻り値がreturnステートメントに置き換えられることがわかります。

包括的な使用例

In [1]: def divide(x, y):...:try:...:         result = x / y
 ...:  except ZeroDivisionError:...:print('division by zero!')...:else:...:print('result is ', result)...:finally:...:print('executing finally clause.')...:         

In [2]:divide(2,0)
division by zero!
executing finally clause.

In [3]:divide(2,1)
result is  2.0
executing finally clause.

In [4]:divide('2','1')
executing finally clause.---------------------------------------------------------------------------
TypeError                                 Traceback(most recent call last)<ipython-input-4-34bb38fa74fd>in<module>()---->1divide('2','1')<ipython-input-1-4273ffa41b76>individe(x, y)1 def divide(x, y):2try:---->3         result = x / y
  4  except ZeroDivisionError:5print('division by zero!')

TypeError: unsupported operand type(s)for/:'str' and 'str'

結論として:

積極的に例外をスローします##

声明を上げる

In [1]: raise NameError('Hello')---------------------------------------------------------------------------
NameError                                 Traceback(most recent call last)<ipython-input-1-64f372e60821>in<module>()---->1 raise NameError('Hello')

NameError: Hello

ユーザー定義の例外##

ユーザーが例外クラスを定義する場合、それは直接または間接的にExceptionクラスから継承する必要があります。

classCustomException(Exception):
 def __init__(self, code, message):
  self.code = code
  self.message = message

try:
 raise CustomException(500,'error')
except CustomException as e:print('{},{}'.format(e.code, e.message))

# 出力結果:500,error

例外配信##

関数で例外が発生したときに例外がキャッチされない場合、例外は関数が呼び出された場所に伝播されます。

In [1]: def a():...:         raise Exception('Hello')...: 

In [2]: def b():...:print('enter b')...:a()  #関数aで発生した例外は、親関数の呼び出しに渡されます
 ...: print('exit b')  #例外がaにスローされた後、それはbに渡され、bの実行は中止されます。
   ...:     

In [3]:b()
enter b
---------------------------------------------------------------------------
Exception                                 Traceback(most recent call last)<ipython-input-3-9c619ddbd09b>in<module>()---->1b()<ipython-input-2-f99a565bd6f8>inb()1 def b():2print('enter b')---->3a()4print('exit b')5<ipython-input-1-6e68e60e93b5>ina()1 def a():---->2         raise Exception('Hello')

Exception: Hello

Recommended Posts

Pythonの例外処理
Pythonの一般的な例外処理メカニズム
Pythonの例外処理
Pythonランタイム例外管理ソリューション
Pythonエラー処理は詳細な説明を主張します
Pythonの例外概念の紹介と処理
Pythonマルチスレッド
Pythonファイル処理の実用ガイド
Python CookBook
Python FAQ
Python3辞書
Python3モジュール
Pythonの基本
Python記述子
Pythonの基本2
Python exec
Python3タプル
Pythonデコレータ
Python IO
Pythonマルチスレッド
Pythonツールチェーン
Python組み込み例外タイプの包括的な要約
Python3リスト
Pythonマルチタスク-日常
Pythonの概要
pythonの紹介
Pythonアナリティック
Pythonの基本
07.Python3関数
Pythonの基本3
Pythonマルチタスクスレッド
Python関数
python sys.stdout
python演算子
Pythonエントリ-3
Centos 7.5 python3.6
Python文字列
pythonキューキュー
Pythonの基本4
Pythonの基本5