Pythonよくあるエラー一覧と解決方法
初心者がよく遭遇する22種類のエラーを、原因・エラーメッセージ・解決方法とともに丁寧に解説します。エラーメッセージを読み解くコツも身につけましょう。
エラーが起きたら、まず最終行のエラーメッセージを確認しましょう。File "〜.py", line XX でエラーが起きた行番号がわかります。エラーの種類(TypeError: など)と説明文を組み合わせると原因を特定できます。
公式の解説もあわせてどうぞ:Python公式チュートリアル「エラーと例外」
エラーメッセージ逆引き表(英語メッセージから探す)
Python のエラーは末尾に英語のメッセージが表示されます。その英文をそのまま下の表から探すと、原因と詳しい解説に最短でたどり着けます。表示されたメッセージ(NameError: の後ろなど)と見比べてください。
| 表示される英語メッセージ(一部) | エラーの種類 | かんたんな意味 | 解説 |
|---|---|---|---|
invalid syntax / incomplete input | SyntaxError | コロン・括弧・クォートの書き忘れなど文法ミス | §1へ |
unexpected EOF while parsing / unterminated string literal | SyntaxError | 括弧やクォートが閉じられないまま行末・ファイル末尾に達した | §1へ |
expected an indented block | IndentationError | 字下げが必要な行がインデントされていない | §2へ |
unexpected indent | IndentationError | 不要な字下げが入っている | §2へ |
inconsistent use of tabs and spaces | TabError | タブとスペースが混在している | §2へ |
name 'x' is not defined | NameError | 未定義の変数/スペルミス | §3へ |
can only concatenate str (not "int") to str | TypeError | 文字列と数値を + で結合した | §4へ |
'float' object cannot be interpreted as an integer | TypeError | 整数が必要な所に小数を渡した(range() 等) | §4へ |
unsupported operand type(s) for ... | TypeError | 型が合わない同士で計算した | §4へ |
'X' object is not callable | TypeError | 関数でないもの(変数・数値など)を () で呼び出した/関数名を変数で上書きした | §4へ |
'X' object is not subscriptable | TypeError | [ ] で添字アクセスできない型(数値・関数など)に添字を付けた | §4へ |
'NoneType' object is not iterable | TypeError | None(戻り値がない関数の結果など)を for やアンパックで回そうとした | §4へ |
unhashable type: 'list' | TypeError | リストなど変更可能な値を辞書のキーや set の要素にした | §4へ |
takes N positional arguments but M were given | TypeError | 関数に渡した引数の個数が合わない(self の付け忘れも該当) | §4へ |
invalid literal for int() with base 10 | ValueError | 数値にできない文字列を int() に渡した | §5へ |
list index out of range | IndexError | リストの範囲外を参照した | §6へ |
string index out of range | IndexError | 文字列の範囲外を参照した | §6へ |
KeyError: 'x' | KeyError | 辞書に存在しないキーを参照した | §7へ |
'X' object has no attribute 'Y' | AttributeError | メソッド名のスペルミス/型違い | §8へ |
'NoneType' object has no attribute ... | AttributeError | None に対してメソッドを呼んだ | §8へ |
No module named 'x' | ModuleNotFoundError | 未インストール/スペルミス/仮想環境 | §9へ |
cannot import name 'X' from 'Y' | ImportError | モジュールはあるが、その中に指定した名前がない/循環インポート | §21へ |
cannot import name 'X' from partially initialized module(circular import) | ImportError | 2つのファイルが互いに import し合う循環インポート | §21へ |
No such file or directory | FileNotFoundError | ファイルパスが間違っている | §10へ |
division by zero | ZeroDivisionError | ゼロで割った | §11へ |
maximum recursion depth exceeded | RecursionError | 再帰の終了条件がなく無限に呼び出した | §12へ |
'utf-8' codec can't decode byte ... | UnicodeDecodeError | 文字コードの指定が実ファイルと不一致 | §13へ |
'cp932' codec can't decode byte ... | UnicodeDecodeError | Windowsで保存したファイルをShift-JIS(cp932)扱いで読んで失敗 | §13へ |
Permission denied | PermissionError | 権限不足/別アプリがファイルを使用中 | §14へ |
local variable referenced before assignment | UnboundLocalError | 関数内で global 宣言を忘れた | §15へ |
math range error | OverflowError | 浮動小数点が表現できる上限を超えた | §17へ |
main thread is not in main loop | RuntimeError | tkinter を別スレッドから直接操作した | §19へ |
StopIteration | StopIteration | next() でイテレータの終端を越えて進めた | §16へ |
MemoryError | MemoryError | 巨大データを一度に読み込みメモリを使い果たした | §18へ |
AssertionError | AssertionError | assert 文の条件が False になった | §20へ |
KeyboardInterrupt | KeyboardInterrupt | 実行中に Ctrl + C を押した/無限ループを手動で止めた | §22へ |
このページ内で Ctrl + F(Mac は ⌘ + F)を押し、英語メッセージの一部を貼り付けて検索すると、該当箇所がすぐ見つかります。下の目次から種類別に探すこともできます。
- 🔤 文法・インデント系
- 🏷️ 名前・型・値系
- 🗂️ リスト・辞書系
- 📦 インポート・ファイル系
- ⚙️ 実行時・その他
1. SyntaxError(構文エラー)
Pythonの文法規則に違反したコードを書いたときに発生します。プログラムの実行前にチェックされるため、1行でもあると何も実行されません。
よくある原因
- コロン(
:)の書き忘れ(if・for・defの行末) - 括弧・クォートの閉じ忘れ
- 全角スペースや全角文字の混入
if x > 0 # コロンがない
print("正の数")
for i in range(5) # コロンがない
print(i)
print("Hello" # 括弧が閉じていない
if x > 0: # コロンを追加
print("正の数")
for i in range(5): # コロンを追加
print(i)
print("Hello") # 括弧を閉じる
日本語環境では全角スペース( )が混入することがあります。エラー行に見た目上の問題がない場合は、全角文字が混入していないか確認しましょう。VSCodeなら全角スペースが可視化されます。
コロンやクォート、括弧のルールがあいまいだとSyntaxErrorは繰り返し起こります。Pythonの基本構文で if・for・def の書き方を一度整理しておくと、根本から減らせます。
2. IndentationError(インデントエラー)
Pythonはインデント(字下げ)でコードブロックを表現します。インデントのズレや混在があるとエラーになります。
よくある原因
- スペースとタブを混在させている
- インデントの深さが揃っていない
- インデントが必要な箇所でされていない
def greet(name):
print("Hello")
print(name) # インデントの深さが違う
if True:
print("OK") # インデントがない(expected an indented block)
def greet(name):
print("Hello")
print(name) # 同じ深さに揃える(スペース4つ)
if True:
print("OK") # ifブロック内は1段階深くインデント
Pythonの慣習ではスペース4つでインデントします。VSCodeでは「インデントをスペースに変換」設定でタブをスペースに統一できます。エディタの設定で「タブをスペースで表示」をオンにすると混在を防げます。
エラーメッセージ別・原因早見表
IndentationError はメッセージで原因がほぼ特定できます。表示された英文と見比べてください。
| エラーメッセージ | 意味 | 直し方 |
|---|---|---|
expected an indented block | インデントすべき行(if・for・def の直後など)が字下げされていない | ブロックの中身を1段階(スペース4つ)下げる。中身を後で書くなら仮に pass を置く |
unexpected indent | インデント不要な行が字下げされている | 行頭の余分なスペースを削除する。コピペ直後によく起きる |
unindent does not match any outer indentation level | インデントの深さがどの階層とも一致しない(タブとスペースの混在が典型) | 該当行を一度行頭まで消して、スペースだけで揃え直す |
inconsistent use of tabs and spaces(TabError) | 同じブロック内でタブとスペースが混在 | 下記のVSCode手順でファイル全体をスペースに統一する |
VSCodeで混在を一括解消する手順
- 右下ステータスバーの「スペース: 4」(または「タブのサイズ」)表示をクリック
- 「インデントをスペースに変換」を選択 → ファイル全体のタブがスペースに置き換わる
- 再発防止に、設定(
Ctrl+,)で「Editor: Insert Spaces」をオン、「Editor: Render Whitespace」をallにすると空白が可視化されて混在に気づけます
それでも解決しない場合は、エラー行だけでなくその1つ上の行のインデントも確認してください。原因がエラー表示行の手前にあることがよくあります。空白の可視化やタブ→スペース変換の設定はVSCodeのセットアップのページにまとめています。
3. NameError(名前エラー)
定義されていない変数・関数・クラスを使おうとしたときに発生します。
よくある原因
- 変数名のスペルミス(
countをcoutnと書くなど) - 変数を代入する前に参照している
- スコープ外の変数を参照している
print(message) # まだ定義していない
# NameError: name 'message' is not defined
total = coutn + 1 # スペルミス
# NameError: name 'coutn' is not defined
message = "Hello" # 使う前に定義する
print(message)
count = 0
total = count + 1 # 正しいスペルで
4. TypeError(型エラー)
異なる型同士の演算や、関数への引数の型が合わないときに発生します。
よくある原因
- 文字列と数値を
+で結合しようとした - 整数型に対して文字列向けのメソッドを呼んだ
- 関数の引数の数が合わない
age = 25
print("年齢は" + age + "歳です")
# TypeError: can only concatenate str (not "int") to str
def add(a, b):
return a + b
add(1, 2, 3)
# TypeError: add() takes 2 positional arguments but 3 were given
age = 25
# 方法1: str()で変換
print("年齢は" + str(age) + "歳です")
# 方法2: f-string(推奨)
print(f"年齢は{age}歳です")
def add(a, b):
return a + b
add(1, 2) # 引数の数を合わせる
| エラーメッセージ | よくある原因 | 直し方 |
|---|---|---|
'X' object is not callable | 関数でないもの(変数・数値・リスト)を () で呼び出した。関数名と同じ名前の変数で上書きしているケースが多い | 同名の変数で関数を潰していないか確認(例: list = [1,2] の後に list(...) は不可) |
'X' object is not subscriptable | 角括弧 [] で添字アクセスできない型(関数・数値・None)に x[0] した | 対象が本当にリスト/辞書/文字列か確認。関数なら () の付け忘れを疑う |
'NoneType' object is not iterable | None を for やアンパックで回した。値を return しない関数の戻り値を使っていることが多い | 関数がちゃんと値を返しているか、変数が None でないか確認 |
unhashable type: 'list' | リストや辞書を、辞書のキーや set の要素に使った(変更可能な型はハッシュ化できない) | キーには (1, 2) のようなタプル(変更不可の型)を使う |
5. ValueError(値エラー)
型は正しいが、値が無効なときに発生します。文字列を整数に変換しようとして失敗するケースが最多です。
よくある原因
- 数字以外の文字列を
int()やfloat()に渡した - リストに存在しない値を
remove()した unpack時の要素数が合わない
num = int("abc")
# ValueError: invalid literal for int() with base 10: 'abc'
num = int("3.14")
# ValueError: invalid literal for int() with base 10: '3.14'
a, b = [1, 2, 3]
# ValueError: too many values to unpack (expected 2)
# 変換前にチェックするか、try-except で対処
text = "abc"
try:
num = int(text)
except ValueError:
print(f"'{text}' は整数に変換できません")
# 小数点を含む文字列はfloat()で変換
num = float("3.14") # 3.14
num_int = int(float("3.14")) # 3
# アンパックの要素数を合わせる
a, b, c = [1, 2, 3]
# または
a, *rest = [1, 2, 3] # a=1, rest=[2,3]
6. IndexError(インデックスエラー)
リストや文字列の存在しないインデックスにアクセスしたときに発生します。
よくある原因
- 要素数と同じインデックスを指定した(0始まりなので最大は
len()-1) - 空リストの要素にアクセスした
- ループ内でインデックス計算を間違えた
items = ["apple", "banana", "cherry"]
print(items[3]) # インデックス3は存在しない(0〜2)
# IndexError: list index out of range
empty = []
print(empty[0]) # 空リスト
# IndexError: list index out of range
items = ["apple", "banana", "cherry"]
# インデックスの範囲を確認してからアクセス
i = 3
if i < len(items):
print(items[i])
else:
print("インデックスが範囲外です")
# 最後の要素は -1 で取得できる
print(items[-1]) # "cherry"
# 空リストチェック
if items:
print(items[0])
7. KeyError(キーエラー)
辞書に存在しないキーにアクセスしたときに発生します。
よくある原因
- キー名のスペルミス
- 存在するか確認せずに直接アクセス
- 大文字・小文字を間違えた(辞書のキーは大文字小文字を区別する)
person = {"name": "Alice", "age": 25}
print(person["email"])
# KeyError: 'email'
print(person["Name"]) # 大文字小文字が違う
# KeyError: 'Name'
person = {"name": "Alice", "age": 25}
# 方法1: get()を使う(キーがなければNoneまたはデフォルト値)
print(person.get("email")) # None
print(person.get("email", "未設定")) # "未設定"
# 方法2: inでキーの存在を確認
if "email" in person:
print(person["email"])
else:
print("emailキーが存在しません")
# 方法3: try-except
try:
print(person["email"])
except KeyError as e:
print(f"キーが見つかりません: {e}")
8. AttributeError(属性エラー)
オブジェクトに存在しない属性やメソッドを呼び出したときに発生します。
よくある原因
- メソッド名のスペルミス(
appendをappnedなど) - 型を間違えた(リストに文字列のメソッドを使うなど)
Noneに対してメソッドを呼んだ
nums = [3, 1, 2]
nums.shorting() # shorting ではなく sort
# AttributeError: 'list' object has no attribute 'shorting'
result = None
result.append(1) # None は append メソッドを持たない
# AttributeError: 'NoneType' object has no attribute 'append'
text = "hello"
text.append("!") # 文字列はappendを持たない
# AttributeError: 'str' object has no attribute 'append'
nums = [3, 1, 2]
nums.sort() # 正しいメソッド名
# Noneチェックをしてからメソッドを呼ぶ
result = [] # 初期値をリストにする
result.append(1)
# 文字列への追加は + か join を使う
text = "hello"
text = text + "!"
# または
text = "".join(["hello", "!"])
# どんなメソッドがあるか確認する方法
print(dir([])) # リストのメソッド一覧
print(dir("")) # 文字列のメソッド一覧
9. ModuleNotFoundError(モジュール未発見エラー)
インポートしようとしたモジュールが見つからないときに発生します。ImportError の一種です。
よくある原因
- モジュールを
pip installしていない - モジュール名のスペルミス
- 仮想環境が有効化されていない
import requests # インストールされていない場合
# ModuleNotFoundError: No module named 'requests'
import numppy # スペルミス
# ModuleNotFoundError: No module named 'numppy'
# ターミナルで pip install を実行する
# pip install requests
# pip install numpy pandas matplotlib
# インストール後に正しいスペルでインポート
import requests
import numpy as np
# インストール済みパッケージの確認
# pip list
# インポートできるか事前チェック(スクリプト内で)
try:
import requests
except ModuleNotFoundError:
print("requestsがインストールされていません")
print("pip install requests を実行してください")
os・sys・math・json・datetime・tkinter などはPythonに最初から含まれています。それ以外のライブラリ(requests・numpy・pandasなど)は pip install が必要です。
どのライブラリをどのコマンドで入れるかは主要ライブラリ一覧(pipインストール早見表)にまとめています。pip 自体が見つからない・python コマンドが動かないときは、まずPythonのインストールで環境を確認してください。
10. FileNotFoundError(ファイル未発見エラー)
指定したパスにファイルが存在しないときに発生します。
よくある原因
- ファイルパスの書き間違い
- カレントディレクトリが想定と異なる
- ファイル名の大文字小文字が違う(特にLinux/Mac)
with open("data.txt", "r") as f:
content = f.read()
# FileNotFoundError: [Errno 2] No such file or directory: 'data.txt'
with open("C:/Users/hoge/myfile.txt", "r") as f:
content = f.read()
# パスが間違っていてもFileNotFoundError
import os
from pathlib import Path
# 現在のディレクトリを確認
print(os.getcwd())
# ファイルの存在確認
path = Path("data.txt")
if path.exists():
with open(path, "r", encoding="utf-8") as f:
content = f.read()
else:
print(f"ファイルが見つかりません: {path.resolve()}")
# try-exceptで安全に開く
try:
with open("data.txt", "r", encoding="utf-8") as f:
content = f.read()
except FileNotFoundError as e:
print(f"エラー: {e}")
# スクリプトと同じフォルダのファイルを確実に開く
script_dir = Path(__file__).parent
data_path = script_dir / "data.txt"
11. ZeroDivisionError(ゼロ除算エラー)
数値をゼロで割ろうとしたときに発生します。
result = 10 / 0
# ZeroDivisionError: division by zero
result = 10 // 0
# ZeroDivisionError: integer division or modulo by zero
result = 10 % 0
# ZeroDivisionError: integer modulo by zero
# 方法1: 事前にゼロチェック
def safe_divide(a, b):
if b == 0:
return None # またはデフォルト値
return a / b
print(safe_divide(10, 2)) # 5.0
print(safe_divide(10, 0)) # None
# 方法2: try-except
try:
result = 10 / b
except ZeroDivisionError:
result = 0
print("0では割れません")
12. RecursionError(再帰エラー)
再帰関数が深すぎて、Pythonの再帰上限(デフォルト1000回)に達したときに発生します。
よくある原因
- 再帰の終了条件(ベースケース)が間違っている
- 終了条件に到達しない無限再帰
def countdown(n):
print(n)
countdown(n - 1) # 終了条件がない無限再帰
countdown(5)
# RecursionError: maximum recursion depth exceeded
# 終了条件(ベースケース)を必ず書く
def countdown(n):
if n <= 0: # ベースケース
print("終了")
return
print(n)
countdown(n - 1)
countdown(5) # 5, 4, 3, 2, 1, 終了
# 再帰が深くなる処理はループに書き換えることも検討
def countdown_loop(n):
while n > 0:
print(n)
n -= 1
print("終了")
# 再帰の上限を変更する場合(慎重に)
import sys
sys.setrecursionlimit(5000)
13. UnicodeDecodeError(文字コードエラー)
ファイルを読み込む際、指定した文字コードと実際のファイルの文字コードが一致しないときに発生します。Windows環境でよく起こります。
よくある原因
- Windowsで作成したCSV/テキストファイルは
cp932(Shift-JIS)の場合がある encodingを指定しないと環境依存のデフォルト設定が使われる
with open("japanese.txt", "r", encoding="utf-8") as f:
content = f.read()
# UnicodeDecodeError: 'utf-8' codec can't decode byte ...
# (ファイルがShift-JISで保存されている場合)
# Shift-JIS(cp932)で開く
with open("japanese.txt", "r", encoding="cp932") as f:
content = f.read()
# 文字コードが不明な場合は errors='replace' か 'ignore'
with open("japanese.txt", "r", encoding="utf-8", errors="replace") as f:
content = f.read()
# chardetで文字コードを自動検出(pip install chardet が必要)
import chardet
with open("japanese.txt", "rb") as f:
raw = f.read()
detected = chardet.detect(raw)
encoding = detected["encoding"]
print(f"検出された文字コード: {encoding}")
content = raw.decode(encoding)
14. PermissionError(権限エラー)
ファイルやディレクトリへのアクセス権限がないときに発生します。
よくある原因
- 他のアプリケーションが同じファイルを開いている(Excelで開いているCSVなど)
- 読み取り専用ファイルへの書き込み
- システムフォルダや保護されたパスへのアクセス
with open("data.csv", "w") as f: # Excelで開いている場合
f.write("name,age\n")
# PermissionError: [Errno 13] Permission denied: 'data.csv'
import os
# 1. 他のアプリでファイルが開いていないか確認してから実行
# 2. try-exceptで対処
try:
with open("data.csv", "w", encoding="utf-8") as f:
f.write("name,age\n")
except PermissionError:
print("ファイルが他のプログラムで使用中か、権限がありません")
print("Excelなど開いているアプリを閉じてから再実行してください")
# 3. 書き込み先を変更する
output_path = os.path.join(os.path.expanduser("~"), "output.csv")
with open(output_path, "w", encoding="utf-8") as f:
f.write("name,age\n")
15. UnboundLocalError(未束縛ローカル変数エラー)
関数内でグローバル変数と同名のローカル変数を代入しようとしたが、代入前に参照してしまったときに発生します。
count = 0
def increment():
print(count) # ここでエラー
count += 1 # 代入があるので count はローカル変数とみなされる
increment()
# UnboundLocalError: local variable 'count' referenced before assignment
count = 0
# 方法1: global宣言を使う
def increment():
global count
print(count)
count += 1
increment() # 0
increment() # 1
# 方法2: 引数と戻り値を使う(より良い設計)
def increment(count):
return count + 1
count = increment(count) # count = 1
count = increment(count) # count = 2
# 方法3: クラスを使って状態を管理する
class Counter:
def __init__(self):
self.count = 0
def increment(self):
self.count += 1
このエラーは変数の「スコープ(有効範囲)」を理解すると避けやすくなります。関数の使い方で引数・戻り値・ローカル変数とグローバル変数の違いを整理しておくのがおすすめです。
16. StopIteration(イテレータ終端エラー)
next() でイテレータを手動で進めようとしたが、要素がなくなったときに発生します。
items = iter([1, 2])
print(next(items)) # 1
print(next(items)) # 2
print(next(items)) # StopIteration(要素がない)
items = iter([1, 2])
# 方法1: next()のデフォルト値を指定
print(next(items, None)) # 1
print(next(items, None)) # 2
print(next(items, None)) # None(エラーにならない)
# 方法2: try-except
items = iter([1, 2])
while True:
try:
item = next(items)
print(item)
except StopIteration:
break
# 方法3: 普通のforループ(最も推奨)
for item in [1, 2]:
print(item)
17. OverflowError(オーバーフローエラー)
浮動小数点数が表現できる最大値を超えたときに発生します。なお、Python の整数型(int)は任意精度なのでオーバーフローしません。
import math
result = math.exp(1000) # e^1000 は float で表現できない
# OverflowError: math range error
result = float(10 ** 400) # int→float変換でオーバーフロー
# OverflowError: int too large to convert to float
import math
from decimal import Decimal
# 対数スケールで計算する
log_result = 1000 * math.log(math.e) # log(e^1000) = 1000
# Decimal モジュールで高精度計算
result = Decimal(10) ** 400 # Decimal は任意精度
# try-except で対処
try:
result = math.exp(1000)
except OverflowError:
result = float("inf") # 無限大として扱う
18. MemoryError(メモリエラー)
プログラムがメモリを使い果たしたときに発生します。巨大なデータを一度にメモリに読み込もうとすると起こりやすいです。
# メモリを大量に使うコード例
huge_list = list(range(10 ** 9)) # 10億要素のリスト
# MemoryError
# 巨大ファイルを一括読み込み
with open("10gb_file.txt", "r") as f:
content = f.read() # 全内容をメモリに展開
# MemoryError
# 方法1: ジェネレータを使う(メモリに全部展開しない)
huge_gen = range(10 ** 9) # ジェネレータは遅延評価
for i in huge_gen:
if i > 100:
break
# 方法2: ファイルを1行ずつ読む
with open("large_file.txt", "r", encoding="utf-8") as f:
for line in f: # 1行ずつ処理
process(line.strip())
# 方法3: pandasのchunksize(大きなCSVを分割処理)
import pandas as pd
for chunk in pd.read_csv("large.csv", chunksize=10000):
process(chunk)
# 方法4: 不要なオブジェクトを明示的に解放
del huge_list
import gc
gc.collect()
コードを工夫してもメモリが足りない、あるいは大きなデータ処理で動作が極端に重い場合は、搭載メモリ(RAM)不足など環境要因のこともあります。目安のスペックはPython学習・開発向けPCの選び方を参考にしてください。
19. RuntimeError(ランタイムエラー)
実行時に様々な原因で発生する汎用エラーです。tkinter を使ったGUIアプリで「メインスレッド以外でGUIを操作した」際に特によく見られます。
よくある原因(tkinter)
- スレッド(
threading)の中から直接Labelの更新などを行った - GUIの初期化前にウィジェットを操作した
import tkinter as tk
import threading
root = tk.Tk()
label = tk.Label(root, text="待機中")
label.pack()
def update_label():
import time
time.sleep(2)
label.config(text="完了!") # スレッド内からGUIを直接更新
thread = threading.Thread(target=update_label)
thread.start()
root.mainloop()
# RuntimeError: main thread is not in main loop
import tkinter as tk
import threading
root = tk.Tk()
label = tk.Label(root, text="待機中")
label.pack()
def background_task():
import time
time.sleep(2)
# GUIの更新はafter()経由でメインスレッドに渡す
root.after(0, lambda: label.config(text="完了!"))
thread = threading.Thread(target=background_task, daemon=True)
thread.start()
root.mainloop()
20. AssertionError(アサーションエラー)
assert 文の条件が False になったときに発生します。デバッグや前提条件チェックに使われます。
def divide(a, b):
assert b != 0, "bはゼロ以外の値を指定してください"
return a / b
result = divide(10, 0)
# AssertionError: bはゼロ以外の値を指定してください
score = -5
assert 0 <= score <= 100, f"スコアが範囲外です: {score}"
# AssertionError: スコアが範囲外です: -5
# assertのエラーメッセージを読んで、条件を満たす値を渡す
result = divide(10, 2) # b != 0 を満たす値を渡す
score = 85
assert 0 <= score <= 100 # OK
# 本番コードではassertの代わりにValueErrorを使うのが推奨
def divide(a, b):
if b == 0:
raise ValueError("bはゼロ以外の値を指定してください")
return a / b
# assert は -O(最適化)フラグで無効化されることに注意
# python -O script.py → assertが全て無視される
21. ImportError(インポートエラー)
モジュール自体は見つかったものの、その中から指定した名前(関数・クラス・変数)を取り出せないときに発生します。「モジュールが丸ごと無い」場合の ModuleNotFoundError(§9) と混同しやすいので、メッセージで見分けます。
よくある原因
- インポートする名前のスペルミス、またはそのバージョンに存在しない名前を指定した
- 2つのモジュールがお互いをインポートし合う「循環インポート」になっている
- 自分のファイル名を標準ライブラリと同じ名前(例:
random.py・json.py)にしてしまい、そちらが読み込まれた
from math import square_root # mathにこの名前は無い(正しくはsqrt)
# ImportError: cannot import name 'square_root' from 'math'
# 自作ファイルを random.py という名前で保存して実行した場合
import random
print(random.randint(1, 6))
# AttributeError や ImportError の原因になる
# (標準のrandomではなく自分のファイルが読み込まれるため)
# 正しい名前でインポートする
from math import sqrt
print(sqrt(16)) # 4.0
# そのモジュールに何があるか一覧で確認する
import math
print(dir(math)) # 使える関数名の一覧が見られる
# 自作ファイル名が標準ライブラリと被っていないか確認する
# random.py → my_random.py などにリネームし、
# 古いキャッシュ(__pycache__ フォルダ)が残っていれば削除する
メッセージに (most likely due to a circular import) と付く場合は、2つのファイルが互いを import し合っています。片方のインポートを関数の中に移す、共通部分を第3のファイルに分けるなどで解消できます。ライブラリのインストール状況を確認したいときは主要ライブラリ一覧もあわせてどうぞ。
22. KeyboardInterrupt(実行中断)
プログラムの実行中に Ctrl + C(Mac も Ctrl + C)を押して処理を止めたときに発生します。多くの場合はバグではなく、あなた自身が止めた合図です。ただし、意図せず無限ループに入ってしまい手動で止めたときにも出ます。
while True:
pass # 何も進まない無限ループ
# 実行中に Ctrl + C を押すと…
# Traceback (most recent call last):
# ...
# KeyboardInterrupt
# Ctrl + C を受け取って、後片付けをしてから終了する
try:
while True:
# 長時間動かす処理など
do_something()
except KeyboardInterrupt:
print("\n中断されました。終了します。")
# ここでファイルを閉じる・保存するなどの後始末を書く
# 無限ループが意図しないものなら、
# ループの終了条件(break や条件式)を見直す
count = 0
while count < 5:
print(count)
count += 1 # これを忘れると無限ループになる
裸の except:(=except BaseException:)は KeyboardInterrupt まで捕まえてしまい、Ctrl + C で止められなくなります。いっぽう except Exception: は KeyboardInterrupt を捕まえない(=Ctrl + C は効く)ので、まとめて例外を処理したいときは裸の except: は避けて except Exception: を使い、中断を自分で扱いたいときは except KeyboardInterrupt: と種類を明示しましょう。
エラー対処の基本ステップ
- エラーの最終行を読む(エラーの種類と説明)
File "〜.py", line XXでエラー行を確認- エラー行とその前後のコードを確認する
- 変数の型・値を
print()で出力して確認する - それでも解決しない場合はエラーメッセージを検索する