Pythonの代表的な例外(Exception)の種類と発生原因をコード例付きで解説
Pythonには、プログラムの中で頻繁に発生する代表的な例外がいくつか存在します。これらの例外は、プログラマが明示的に発生させる場合もあれば、Pythonインタプリタが暗黙的に検出して発生させる場合もあります。ここでは、特によく見かける主要な例外について、その発生条件と実際のコード例・実行結果を交えて詳しく解説します。
AssertionError(アサーションエラー)
assert文の条件が偽(False)になった場合に発生する例外です。Pythonではコード内にassert文を記述でき、その条件は常に真であることが期待されます。条件が満たされなかった瞬間にAssertionErrorが送出されます。
コード例
class MyClass:
def __init__(self, x):
self.x = x
assert self.x > 50
myObj = MyClass(5)
実行結果
--------------------------------------------------------------------------- AssertionError Traceback (most recent call last) <ipython-input-21-71785acdf821> in <module>() ----> 6 myObj = MyClass(5) <ipython-input-21-71785acdf821> in __init__(self, x) ----> 4 assert self.x > 50 AssertionError:
AttributeError(アトリビュートエラー)
クラスやオブジェクトが持っていない属性(メンバ変数やメソッド)にアクセスしようとした際に発生する例外です。
コード例
class point:
def __init__(self, x=0, y=0):
self.x = x
self.y = y
def getpoint(self):
print('x= ' + str(self.x))
print('y= ' + str(self.y))
print('z= ' + str(self.z))
pt = point(10, 20)
pt.getpoint()
実行結果
x= 10
y= 20
---------------------------------------------------------------------------
AttributeError Traceback (most recent call last)
---> 12 pt.getpoint()
<ipython-input-15-f64eb52b2192> in getpoint(self)
----> 9 print('z= ' + str(self.z))
AttributeError: 'point' object has no attribute 'z'
この例では、pointクラスにzという属性が定義されていないため、アクセスした時点でAttributeErrorが発生しています。
ImportError(インポートエラー)
import文によるモジュールの読み込みに問題が生じた場合に発生する例外です。また、from文で指定したパッケージ名は正しいものの、そこからインポートしようとした名前のモジュール(または名前)が存在しない場合にも送出されます。
コード例
from math import abcd
実行結果
--------------------------------------------------------------------------- ImportError Traceback (most recent call last) ----> 1 from math import abcd ImportError: cannot import name 'abcd'
mathモジュール自体は存在しますが、「abcd」という名前は定義されていないため、インポートに失敗します。
ModuleNotFoundError(モジュール未検出エラー)
ImportErrorのサブクラスです。指定されたモジュールが見つからない場合に発生します。sys.modulesの中にNoneが見つかった場合にも送出されることがあります。
コード例
import abcd
実行結果
--------------------------------------------------------------------------- ModuleNotFoundError Traceback (most recent call last) ----> 1 import abcd ModuleNotFoundError: No module named 'abcd'
IndexError(インデックスエラー)
リスト・タプルなどのシーケンス型に対して、範囲外の添字(インデックス)でアクセスしようとした際に発生する例外です。
コード例
myList = [10, 20, 30, 40] print(str(myList[5]))
実行結果
---------------------------------------------------------------------------
IndexError Traceback (most recent call last)
1 myList = [10, 20, 30, 40]
----> 2 print(str(myList[5]))
IndexError: list index out of range
このリストの有効なインデックスは0〜3までなので、5番目へのアクセスは範囲外となりエラーになります。
RecursionError(再帰エラー)
実行時エラーの一種で、関数の再帰呼び出しが最大再帰深度(デフォルトで約1000回)を超えた場合に発生します。
コード例
def myFunction(): myFunction() myFunction()
実行結果
--------------------------------------------------------------------------- RecursionError Traceback (most recent call last) ----> 4 myFunction() <ipython-input-39-8a59e0fb982f> in myFunction() ----> 2 myFunction() ... last 1 frames repeated, from the frame below ... <ipython-input-39-8a59e0fb982f> in myFunction() ----> 2 myFunction() RecursionError: maximum recursion depth exceeded
この関数には終了条件がないため、自分自身を無限に呼び続け、最終的にRecursionErrorとなります。
StopIteration(ストップイテレーション)
組み込み関数next()を使ってイテレータから次の要素を取得しようとした際、それ以上要素が存在しない場合に発生する例外です。
コード例
myList = [10, 20, 30, 40] myIter = iter(myList) while True: print(next(myIter))
実行結果
10 20 30 40 --------------------------------------------------------------------------- StopIteration Traceback (most recent call last) ----> 4 print(next(myIter)) StopIteration:
すべての要素を出力し終えた後、next()がさらに次の要素を要求したためStopIterationが送出されています。
IndentationError(インデントエラー)
Pythonのコードに不正なインデント(字下げ)が含まれている場合に発生する例外です。PythonのSyntaxErrorクラスを継承しており、構文エラーの一種として扱われます。
コード例
for i in range(10):
print("The value of i: " + str(i))
実行結果
File "<ipython-input-44-d436d50bbdc8>", line 2
print("The value of i: " + str(i))
^
IndentationError: expected an indented block
forブロックの中身は必ずインデントする必要があります。上の例ではインデントがないためエラーになっています。
TypeError(タイプエラー)
不適切な型のオブジェクトに対して操作を実行しようとした際に発生する例外です。たとえば、リストのインデックスに浮動小数点数を指定するとTypeErrorが返されます。
コード例
myList = [10, 20, 30, 40] print(myList[1.25])
実行結果
---------------------------------------------------------------------------
TypeError Traceback (most recent call last)
1 myList = [10, 20, 30, 40]
----> 2 print(myList[1.25])
TypeError: list indices must be integers or slices, not float
リストのインデックスには整数またはスライスしか使用できないため、float型の値を渡すとエラーになります。
ZeroDivisionError(ゼロ除算エラー)
除算において分母が0(ゼロ)である場合に発生する例外です。
コード例
print(5/0)
実行結果
--------------------------------------------------------------------------- ZeroDivisionError Traceback (most recent call last) ----> 1 print(5/0) ZeroDivisionError: division by zero
数学的に0での割り算は定義されていないため、Pythonはこの例外を発生させてプログラムの異常を通知します。
まとめ
これらの例外は、いずれもPythonの組み込み例外クラス階層に属しており、try-except文を使って適切に捕捉・処理することができます。各例外の発生条件を理解しておくことで、エラーの原因特定が速くなり、より堅牢なPythonプログラムを書くことにつながります。
-
Pythonで二分木の直径を求める方法【DFSを使った実装解説】
二分木の直径とは二分木が与えられたとき、その木の直径(diameter)を計算することを考えます。二分木の直径とは、木の中の任意の2つのノードをつなぐ最長経路の長さのことです。重要なポイントとして、この経路は必ずしも根(ルート)を通るとは限りません。例えば、次のような木を考えてみましょう。この場合、経路 [4, 2, 1, 3] または [5, 2, 1, 3] の長さが3本の辺で構成されているため、直径は3となります。解法のアプローチこの問題はDFS(深さ優先探索)を使うことで効率的に解くことができます。手順は以下の通りです。DFSで各ノードを訪問しながら直径を求めます。まず答えを格納する変
-
Pythonの継承とは?単一継承と階層継承の基本をサンプルコードで解説
本記事では、Python 3.xにおける継承(インヘリタンス)とクラスの拡張方法について詳しく解説します。 継承とは、現実世界のモノや概念の関係性を自然に表現できる、オブジェクト指向プログラミングの中核となる仕組みです。継承を活用すると、次のようなメリットが得られます。 再利用性:すでに書いたコードを流用でき、重複を削減できる 推移性:クラス間の関係を連鎖的に引き継げる 開発速度の向上:ゼロから書かずに済むため、短期間で開発できる 保守性・拡張性:既存クラスを壊さずに機能を追加しやすい 継承の5つの種類 Pythonの継承は、その構造によって主に以下の5種類に分類されます。 単一継承(