動画
課題
課題(チャプター8:例外処理)
【基本問題】例外の必要性と起きうる例外(5問)
問題1
変数n = 0として、print(10 / n)を実行するプログラムを書いたとき、どの種類の例外が発生するかを答えるため、例外が発生するコードをそのまま書き、実行して例外名を確認してください(提出物は「例外名が分かる形」でよいです)。
期待される出力(例・例外メッセージの先頭):
ZeroDivisionError: division by zero
ヒント: ゼロ除算はZeroDivisionErrorです。
問題2
次の式を評価するコードを書いたとき、どの例外が起きるか確認してください。print("hello" + 3)
期待される出力(例・例外メッセージの先頭):
TypeError: can only concatenate str (not "int") to str
ヒント: 型が合わない操作はTypeErrorになります(環境によりメッセージの細部は異なる場合があります)。
問題3
リストitems = ["A", "B", "C"]に対してprint(items[3])を実行するコードを書き、発生する例外を確認してください。
期待される出力(例・例外メッセージの先頭):
IndexError: list index out of range
ヒント: 範囲外のインデックスはIndexErrorです。
問題4
辞書scores = {"数学": 80}に対してprint(scores["英語"])を実行するコードを書き、発生する例外を確認してください。
期待される出力(例・例外メッセージの先頭):
KeyError: '英語'
ヒント: 存在しないキーはKeyErrorです。
問題5
int("abc")をprintで評価しようとするコードを書き、発生する例外を確認してください。
期待される出力(例・例外メッセージの先頭):
ValueError: invalid literal for int() with base 10: 'abc'
ヒント: 台本情報整理にもある通り、数値に変換できない文字列はValueErrorです。
【基本問題】try / except の基本(10問)
問題6
辞書stock = {"りんご": 10, "みかん": 5}と変数code = "ぶどう"を用意し、tryでprint(stock[code])を実行し、KeyErrorのときにprint("在庫がありません")するプログラムを作成してください。
期待される出力:
在庫がありません
ヒント: except KeyError:のインデントとコロンに注意します。
問題7
問題6と同じstockを使い、code = "みかん"のときに在庫が表示されるプログラムを作成してください(例外は起きない想定)。
期待される出力:
5
ヒント: キーが存在すればtry内のprintだけが動きます。
問題8
変数s = "12"に対し、tryでprint(int(s))を実行し、ValueErrorのときはprint("数値にできません")するプログラムを作成してください。
期待される出力:
12
ヒント: この設定では例外は起きません。
問題9
変数s = "abc"に対し、問題8と同じ例外処理を行うプログラムを作成してください。
期待される出力:
数値にできません
ヒント: int(...)が失敗するとValueErrorです。
問題10
変数a = 10、b = 0を用意し、tryでprint(a / b)を実行し、ZeroDivisionErrorのときはprint("0では割れません")するプログラムを作成してください。
期待される出力:
0では割れません
ヒント: 台本のゼロ除算デモをtry版にしたイメージです。
問題11
tryの中で1 / 0を実行し、except ZeroDivisionErrorでprint("NG")したあと、tryの外でprint("続行")を実行するプログラムを作成してください。
期待される出力:
NG
続行
ヒント: 例外を拾うとexceptのあと処理が続けられます。
問題12
次のコードはexceptのインデントが壊れています。正しく直して、KeyErrorのときにOKと表示されるようにしてください。
d = {"x": 1}
try:
print(d["y"])
except KeyError:
print("OK")
期待される出力:
OK
ヒント: exceptブロックもifと同様にインデントが必要です。
問題13
辞書stockとcode = "りんご"を使い、tryでqty = stock[code]を取得し、KeyErrorのときはprint("未登録")、成功したらprint("在庫", qty)をtry内で実行するプログラムを作成してください。
期待される出力:
在庫 10
ヒント: まずはelseなしで、成功時の表示をtry内に書いてもよいです。
問題14
1つのtryに対し、except KeyErrorとexcept ZeroDivisionErrorを2つ並べる形で、b = 0のときにゼロ除算を拾ってprint("Z")するプログラムを作成してください(辞書参照は行わなくてよい)。
期待される出力:
Z
ヒント: 台本にある「exceptを並べる」形の練習です。
問題15
辞書stock = {"りんご": 10}とcode = "りんご"、n = 2を用意し、tryでprint(stock[code] / n)を実行し、KeyErrorのときはprint("K")、ZeroDivisionErrorのときはprint("Z")するプログラムを作成してください。
期待される出力:
5.0
ヒント: この条件ではどちらの例外も起きません。
【基本問題】except … as e(6問)
問題16
辞書stock = {"りんご": 10}、code = "ぶどう"に対し、except KeyError as e:でprint("NG", e)するプログラムを作成してください。
期待される出力:
NG 'ぶどう'
ヒント: KeyErrorのeには存在しなかったキー情報が載ります。
問題17
tryでint("xyz")を実行し、except ValueError as e:でprint(str(e))するプログラムを作成してください。
期待される出力:
invalid literal for int() with base 10: 'xyz'
ヒント: str(e)でメッセージ文字列化できます。
問題18
tryで1 / 0を実行し、except ZeroDivisionError as e:でprint(type(e).__name__)を表示するプログラムを作成してください。
期待される出力:
ZeroDivisionError
ヒント: 例外オブジェクトもオブジェクトです。
問題19
リストnums = [1, 2]に対し、tryでprint(nums[5])を実行し、except IndexError as e:でprint("ERR")だけを表示するプログラムを作成してください(eの中身の表示は不要)。
期待される出力:
ERR
ヒント: as eは必ずしも表示に使う必要はありませんが、書く練習にします。
問題20
tryでraise ValueError("テスト")を実行し、except ValueError as e:でprint(e.args)を表示するプログラムを作成してください。
期待される出力:
('テスト',)
ヒント: 例外の引数はargsタプルに入ります。
問題21
辞書stock = {"A": 1}、code = "B"に対し、tryでprint(stock[code])を実行し、except KeyError as e:でprint("key=", repr(e.args[0]))を表示するプログラムを作成してください。
期待される出力:
key= 'B'
ヒント: どのキーで失敗したかをログ向けに残すイメージです。
【基本問題】else(例外が起きなかったとき)(6問)
問題22
辞書stock = {"りんご": 10, "みかん": 5}、code = "みかん"に対し、tryでqty = stock[code]を取得し、except KeyErrorでprint("NG")、elseでprint("OK", qty)するプログラムを作成してください。
期待される出力:
OK 5
ヒント: 台本のelse例と同じ考え方です。
問題23
問題22と同じ構造で、code = "ぶどう"にしたときの出力になるプログラムを作成してください。
期待される出力:
NG
ヒント: 例外が起きるとelseは実行されません。
問題24
変数s = "7"に対し、tryでn = int(s)を実行し、except ValueErrorでprint("bad")、elseでprint("num", n)するプログラムを作成してください。
期待される出力:
num 7
ヒント: 成功時だけelseが動きます。
問題25
tryでx = 10 / 2を計算し、except ZeroDivisionErrorでprint("Z")、elseでprint(int(x))するプログラムを作成してください。
期待される出力:
5
ヒント: 割り算が成功すればelseへ進みます。
問題26
tryでdata = {"a": 1}["a"]を取得し、except KeyErrorでprint("K")、elseでprint("V", data)するプログラムを作成してください。
期待される出力:
V 1
ヒント: elseは「例外が一切起きなかったときだけ」です。
問題27
次のコードはelseの位置が誤っています(構文エラーまたは意図しない動きになります)。try/except/elseの正しい並びに直し、code = "x"のときにOK 1と表示されるようにしてください。
d = {"x": 1}
code = "x"
try:
v = d[code]
except KeyError:
print("NG")
print("OK", v)
期待される出力:
OK 1
ヒント: 成功時だけの表示をelse:ブロックへ移します。
【基本問題】finally(必ず実行)(8問)
問題28
tryでprint(1)を実行し、except ValueErrorでprint("E")、finallyでprint("END")するプログラムを作成してください(例外は起きません)。
期待される出力:
1
END
ヒント: finallyは例外の有無に関わらず最後に実行されます。
問題29
tryで1 / 0を実行し、except ZeroDivisionErrorでprint("Z")、finallyでprint("END")するプログラムを作成してください。
期待される出力:
Z
END
ヒント: 例外が起きてもfinallyは必ず走ります。
問題30
辞書stock = {"りんご": 0, "みかん": 5}、code = "りんご"に対し、tryでqty = stock[code]してからprint(10 / qty)を実行し、except (KeyError, ZeroDivisionError)でprint("NG")、finallyでprint("---")するプログラムを作成してください。
期待される出力:
NG
---
ヒント: 台本の「タプルで複数型をまとめて拾う」例です。
問題31
問題30と同じstockでcode = "みかん"にしたとき、print(10 / qty)が成功するプログラムを作成してください(例外処理の形は同じでよい)。
期待される出力:
2.0
---
ヒント: 成功してもfinallyは実行されます。
問題32
try/except/else/finallyをすべて使い、次の順で表示されるプログラムを作成してください。try内はx = 2だけ、exceptは到達しない想定、elseでprint("A", x)、finallyでprint("B")。
期待される出力:
A 2
B
ヒント: 台本どおり、elseはfinallyの前です。
問題33
tryでraise ValueErrorを発生させ、except ValueErrorでprint("C")、elseでprint("D")(実行されない)、finallyでprint("B")するプログラムを作成してください。
期待される出力:
C
B
ヒント: 例外が起きた場合、elseはスキップされます。
問題34
tryでprint("X")を実行し、finallyだけを付けた形(exceptなし)で、最後にprint("Y")を表示するプログラムを作成してください。
期待される出力:
X
Y
ヒント: tryにfinallyだけを付けることはできます(教材の範囲として知識として押さえる)。
問題35
カウンタ風に、count = 0を用意し、tryでcount += 1と1/0を実行、except ZeroDivisionErrorでcount += 10、finallyでcount += 100し、最後にprint(count)するプログラムを作成してください。
期待される出力:
111
ヒント: try内で例外が起きた後の行は実行されませんが、finallyは必ず実行されます。
【基本問題】raise(意図的に例外を投げる)(6問)
問題36
変数code = ""(空文字)に対し、if not code.strip():のときにraise RuntimeError("コードを入力してください")し、tryの外ではなくtry内で行い、except RuntimeError as e:でprint(e)するプログラムを作成してください。
期待される出力:
コードを入力してください
ヒント: 台本のraise RuntimeError例です。
問題37
変数code = "りんご"、辞書stock = {"りんご": 10}に対し、try内で空チェックのあとprint(stock[code])を実行し、except RuntimeErrorとexcept KeyErrorを並べて拾うプログラムを作成してください(空ではないので在庫が表示されます)。
期待される出力:
10
ヒント: 台本の「空ならraise、無いキーはKeyError」の分岐練習です。
問題38
変数n = -1に対し、n < 0ならraise ValueError("負数は不可")し、except ValueError as e:でprint(e)するプログラムを作成してください。
期待される出力:
負数は不可
ヒント: 先にifでガードし、契約違反を早めに止める書き方です。
問題39
try内でraise ValueError("A")を実行し、except ValueErrorでprint("caught")のあとraise単体で再送出し、外側のtry/except ValueErrorで最終的にprint("outer")するプログラムを作成してください。
期待される出力:
caught
outer
ヒント: raise単体は「今の例外をそのまま投げ直す」用途です。
問題40
関数def only_positive(x):を定義し、x <= 0ならraise ValueError("正の数のみ")、そうでなければreturn x * 2としてください。print(only_positive(3))を呼び出すプログラムを作成してください。
期待される出力:
6
ヒント: raiseは関数の中からでも使えます。
問題41
問題40の関数に対し、tryでonly_positive(0)を呼び、except ValueErrorでprint("fix")するプログラムを作成してください。
期待される出力:
fix
ヒント: 呼び出し元で拾うと「部品は失敗を投げ、外側で扱う」形になります。
【基本問題】例外の伝播(4問)
問題42
辞書stock = {"りんご": 10}と関数def get_qty(code): return stock[code]を定義し、外側でtryしてprint(get_qty("みかん"))を実行、except KeyErrorでprint("画面向け: 扱っていません")するプログラムを作成してください。
期待される出力:
画面向け: 扱っていません
ヒント: 台本の伝播例(関数内で起きたKeyErrorを外で捕まえる)です。
問題43
問題42と同じ関数で、print(get_qty("りんご"))を実行するプログラムを作成してください。
期待される出力:
10
ヒント: 例外が起きなければexceptには入りません。
問題44
関数def inner():で1/0を実行し、関数def outer():からinner()を呼び、さらにメインでtry/except ZeroDivisionErrorしてprint("saved")するプログラムを作成してください。
期待される出力:
saved
ヒント: 例外は呼び出し元へ伝わります。
問題45
関数def work(): raise KeyError("x")を定義し、呼び出し側でtry/except KeyError as e:してprint("err", e)するプログラムを作成してください。
期待される出力:
err 'x'
ヒント: 下位で投げた例外を上位でメッセージ化する練習です。
【発展問題】複合except・運用・独自例外(5問)
問題46
変数s = "5"に対し、tryでn = int(s)とprint(10 / (n - 5))を実行し、except (ValueError, ZeroDivisionError)でprint("bad")するプログラムを作成してください。
期待される出力:
bad
ヒント: 1つのexceptにタプルで複数型を列挙できます。
問題47
次のコードは例外を無言に飲み込みます。台本情報整理の注意どおり、passではなくユーザーに分かる出力に変えてください。
try:
int("x")
except ValueError:
pass
期待される出力:
入力が不正です
ヒント: except: passは原則避け、理由が必要ならコメント+ログ等を検討します。
問題48
次のコードはExceptionまで広く拾いすぎです。ValueErrorだけを拾うように修正し、int("1")が成功してprint(n)が実行されるようにしてください。
try:
n = int("1")
except Exception:
print("E")
else:
print(n)
期待される出力:
1
ヒント: 教材では「具体的な例外型」を基本にします。
問題49
台本の発展例に倣い、class OutOfStockError(Exception):を定義(本文はpassでよい)し、raise OutOfStockError("在庫ゼロ")をtry内で実行、except OutOfStockError as e:でprint(e)するプログラムを作成してください。
期待される出力:
在庫ゼロ
ヒント: チャプター7のクラス定義の延長として捉えます。
問題50
次の仕様を満たすプログラムを作成してください。辞書stock = {"りんご": 10, "みかん": 0}、変数code = "みかん"。tryでqty = stock[code]を取得し、qty == 0ならraise ValueError("在庫0")。except KeyErrorでprint("K")、except ValueError as e:でprint("V", e)、finallyでprint("done")。
期待される出力:
V 在庫0
done
ヒント: 「辞書にキーはあるが在庫が0」など、業務ルールはraiseで明示すると読み手に伝わりやすいです。
