Python でカスタム例外を作成する

Rayven Esplanada 2023年10月10日
  1. Python でカスタム例外クラスを作成する
  2. Python で try...except ブロックを使用して例外処理を実行する
Python でカスタム例外を作成する

このチュートリアルでは、Python でカスタム例外クラスを作成できることを示します。ここでは、例外処理を適切に実行し、カスタム例外クラスを定義し、既存の組み込み例外をオーバーライドする方法を示します。

例外は、プログラム内の何かが意図したとおりに進まなかったり、プログラムの意図されたユースケースの流れを妨害したりするたびに発生するタイプのイベントです。例外処理がないと、プログラムは完全に実行されなくなり、例外を修正または処理する必要があります。

Python でカスタム例外クラスを作成する

Python での例外クラスの作成は、通常のクラスと同じ方法で行われます。主な違いは、作成しているクラスが例外クラスであることをコンパイラに通知するために、Python の基本 Exception クラスを含める必要があることです。

このメソッドをテストして、DemoException という例外クラスを作成し、プレースホルダー制御フローキーワード pass をプレースホルダーとして使用してみましょう。

class DemoException(Exception):
    pass

Python でキーワード raise を使用して例外発生を実行する

DemoException クラスをテストし、実際にトリガーされたときに何が表示されるかを確認するには、例外の発生を実行します。例外の発生は、他のプログラミング言語での例外のスローと同義です。

キーワード raise を使用して、指定された例外クラスを使用して例外をトリガーし、例外メッセージを出力します。

class DemoException(Exception):
    pass


raise DemoException

出力:

Traceback (most recent call last):
  File "/Users/demo/python/demo_exception.py", line 4, in <module>
    raise DemoException
__main__.DemoException

カスタム例外メッセージが宣言されていない場合、標準の例外はターミナルのようになります。

Python でカスタム例外メッセージを宣言する

DemoException のカスタム例外メッセージを宣言するには、例外クラスの __init__() メソッドをオーバーライドし、必須の自己参照パラメーターself とともに、例外に対して出力する必要のあるメッセージをパラメーターに含めます。

たとえば、__init__() メソッドをオーバーライドして、DemoException クラスのカスタムメッセージを作成しましょう。

class DemoException(Exception):
    def __init__(self, message):
        super().__init__(message)

メッセージが例外に正常に統合されるようにするには、基本の Exception クラス、__init__() メソッドを呼び出し、引数として message を含めることに注意してください。

raise キーワードを使用して例外クラスを再度呼び出し、カスタムメッセージを渡します。

class DemoException(Exception):
    def __init__(self, message):
        super().__init__(message)


message = "Exception Triggered! Something went wrong."
raise DemoException(message)

出力は次のようになります。

Traceback (most recent call last):
  File "/Users/demo/python/helloworld.py", line 6, in <module>
    raise DemoException(message)
__main__.DemoException: Exception Triggered! Something went wrong.

これで、カスタムエラーメッセージを含む例外クラスが正常に作成され、トリガーされました。

例外をトリガーする可能性のある実際の状況では、これらの例外をどのように処理して発生させるのですか?try...except ブロックを使用して例外処理を実装することで、この問題を適切に解決できます。

Python で try...except ブロックを使用して例外処理を実行する

try...except ブロックは、Java などの他の言語の try-catch ブロックによく似ています。

try...except ブロックには、2つのメインブロックと 2つのオプションブロックがあります。

  • try(必須)-例外がトリガーされる可能性のあるコードブロックのカプセル化を担当するメインブロック。try ブロックは、例外がトリガーされるたびに、その中のプロセス全体を停止します。
  • except(必須)-ブロックプログラムは、指定された例外がトリガーされるたびに続行します。このブロックには通常、呼び出し元に対する説明的なエラーメッセージ、または単純な print() ステートメントが含まれています。1つの try ブロックに複数の except ブロックが存在する場合があり、それぞれが異なる例外をキャッチします。
  • else(オプション)-このオプションのブロックは、try ブロックが例外をトリガーしなかった場合にプログラムが続行する場所です。
  • finally(オプション)-このオプションのブロックは、例外がトリガーされたかどうかに関係なく、前の 3つのブロックのすべてが実行されると実行されます。

DemoException クラスを使用する前の例を使用して、単純な try...except ブロックを試してみましょう。

まず、raise キーワードを関数でラップし、try...except ブロック内に配置します。

この例で作成する関数は、数値を受け入れ、0 を送信すると例外をスローする関数です。他の番号を送信する場合、コードは意図したとおりに続行されます。以下の例を確認してください。

class DemoException(Exception):
    def __init__(self, message):
        super().__init__(message)


message = "Exception Triggered! Something went wrong."


def triggerException(num):
    if num == 0:
        raise DemoException(message)
    else:
        print(num)


try:
    triggerException(0)
    print("Code has successfully been executed.")
except DemoException:
    print("Error: Number should not be 0.")

triggerException() が引数として 0 を渡したため、コードは DemoException をトリガーする必要があります。ここでは、raise キーワードメッセージが、出力として except ブロック内にあるもので上書きされることを期待する必要があります。

triggerException() 関数呼び出しの後の print() 行が出力されなかったことに注意してください。これは、関数が例外を発生させたためです。したがって、try ブロック内のすべてのプロセスを即座に停止し、except ブロックに直接進みました。

出力:

Error: Number should not be 0.

それでは、たとえば 20 のような有効な番号を渡してみましょう。

try:
    triggerException(20)
    print("Code has successfully been executed.")
except DemoException:
    print("Error: Number should not be 0.")

出力:

20
Code has successfully been executed.

except ブロックをチェーンして、別の例外を作成してみましょう。指定された入力が数値でない場合にトリガーされる新しい例外 NumberFormatException を呼び出しましょう。この例外クラスでは、クラス内でメッセージを宣言しましょう。

class NumberFormatException(Exception, value):
    message = f"{value} is not a number"

    def __init__(self):
        super().__init__(message)

次に、上記のコードを変更して、新しい例外クラス NumberFormatException を処理します。

class DemoException(Exception):
    def __init__(self, message):
        super().__init__(message)


class NumberFormatException(Exception):
    def __init__(self, message, value):
        message = f"{value} is not a number"
        super().__init__(message)


message = "Exception occured."


def triggerException(num):
    if not num.isdigit():
        raise NumberFormatException(message, num)
    elif num == 0:
        raise DemoException(message)
    else:
        print(num)


num = "sample string"
try:
    triggerException(num)
    print("Code has successfully been executed.")
except DemoException:
    print("Error: Number should not be 0.")
except NumberFormatException:
    print(num + " is not a number.")

このコードでは、triggerException() に渡された num の値は文字列'sample string'であるため、NumberFormatException をトリガーする必要があります。

出力:

sample string is not a number.

要約すると、Python でカスタム例外を作成するのは、新しいクラスを作成するのと同じくらい簡単ですが、クラス定義の追加の引数として Exception クラスを使用します。raise キーワードは、例外クラスを指定して例外をトリガーするために使用されます。try...except ブロックは、コードブロック内で 1つ以上の例外をラップし、プログラムを完全にシャットダウンするだけでなく、その例外を処理するときにコードが行うことを変更するために使用されます。

Rayven Esplanada avatar Rayven Esplanada avatar

Skilled in Python, Java, Spring Boot, AngularJS, and Agile Methodologies. Strong engineering professional with a passion for development and always seeking opportunities for personal and career growth. A Technical Writer writing about comprehensive how-to articles, environment set-ups, and technical walkthroughs. Specializes in writing Python, Java, Spring, and SQL articles.

LinkedIn

関連記事 - Python Exception