関数の戻り値は、関数が計算した結果を呼び出し元へ手渡す仕組みです。
この記事では、Python初心者が必ず押さえたい戻り値の基礎として、return
の使い方、戻り値がない時のNone
、複数の値を返す方法、そして実務で役立つコツや注意点を、具体例と出力つきで丁寧に解説します。
Pythonの関数の戻り値とは(returnの基本)
戻り値の意味と役割
関数は「入力を受け取り、処理して、結果を返す」小さな部品です。
ここでいう結果が戻り値です。
戻り値があるからこそ、関数の結果を変数に入れて再利用したり、別の計算に組み込んだりできます。
Pythonではreturn
文で戻り値を返し、その瞬間に関数の実行は終了します。
例: 和を返す関数
# 2つの数値の和を「返す」関数
def add(a, b):
# 計算した結果をreturnで呼び出し元に渡します
return a + b
# 戻り値を変数xに受け取り、さらに再利用できます
x = add(2, 3)
print("x =", x)
print("x * 10 =", x * 10)
x = 5
x * 10 = 50
returnの書き方と位置
return 値
の形で書き、関数のどこに置いてもそこが関数の終了点になります。
条件ごとに早めにreturn
することで、読みやすく保守しやすいコードになります。
# スコアに応じて評価を返す。条件ごとに早期returnで分岐を明快に
def grade(score):
if score < 0 or score > 100:
return "invalid" # ここで関数が終了
if score >= 80:
return "A" # ここで関数が終了
if score >= 65:
return "B" # ここで関数が終了
return "C" # すべてに当てはまらなければ最後に返す
print(grade(92))
print(grade(-3))
A
invalid
printとの違い(結果を返す/表示する)
return
は「値を呼び出し元に返す」、print
は「画面に表示する」だけです。
テストや再利用にはreturn
が必須です。
項目 | return | |
---|---|---|
役割 | 値を呼び出し元に渡す | 文字列を標準出力に表示 |
使いどころ | 計算結果の受け渡し、再利用、テスト | デバッグ表示、ログ |
実行への影響 | その時点で関数を終了する | 関数は継続、戻り値は増えない |
返る先 | 呼び出し元の変数や式 | 画面(コンソール) |
def add_with_print(a, b):
# 計算結果を「表示するだけ」
print("add_with_print:", a + b)
def add_with_return(a, b):
# 計算結果を「返す」
return a + b
r1 = add_with_print(2, 3) # 表示はされるが戻り値はNone
r2 = add_with_return(2, 3) # 戻り値5を受け取れる
print("r1は", r1)
print("r2は", r2)
print("r2の2倍は", r2 * 2)
add_with_print: 5
r1は None
r2は 5
r2の2倍は 10
printは戻り値ではありません。
printの結果は別の計算に使えない点に注意してください。
Noneを理解する(戻り値がない時)
returnを書かない時の戻り値(None)
Pythonでは、関数内にreturn
が無い場合、自動的にNone
が返ります。
これは「何も返していない」ことを表す特別な値です。
def greet(name):
# これは表示するだけで、戻り値は用意していません
print("Hello,", name)
result = greet("Alice")
print("戻り値:", result, type(result))
Hello, Alice
戻り値: None <class 'NoneType'>
空のreturnの挙動(None)
return
だけを書いた場合も戻り値はNone
です。
return None
と同じ意味です。
def maybe_even(n):
if n % 2 != 0:
return # ここでNoneが返る
return n # 偶数ならnを返す
print(maybe_even(3)) # 奇数
print(maybe_even(4)) # 偶数
None
4
Noneの判定方法(is None)
None
の判定はis None
/is not None
を使います。
== None
は推奨されません。
def safe_divide(a, b):
if b == 0:
return None # 計算できない時はNoneを返す
return a / b
q1 = safe_divide(10, 0)
q2 = safe_divide(10, 2)
if q1 is None:
print("q1は計算不可")
if q2 is not None:
print("q2 =", q2)
q1は計算不可
q2 = 5.0
複数の値を返す(Python)
タプルで複数返す
Pythonではカンマ区切りで複数の値を返すと、タプル(tuple)として返せます。
括弧は省略可能ですが、読みやすさのために付けても良いです。
# 個数・合計・平均を一度に返す関数
def stats(xs):
count = len(xs)
total = sum(xs)
avg = total / count if count else None
return count, total, avg # タプル(複数値)で返す
受け取り方(アンパック)
返ってきたタプルは、変数を並べて受け取る「アンパック」ができます。
もちろんタプルのまま1変数で受け取ることも可能です。
# 個数・合計・平均を一度に返す関数
def stats(xs):
count = len(xs)
total = sum(xs)
avg = total / count if count else None
return count, total, avg # タプル(複数値)で返す
nums = [10, 20, 30]
n, s, avg = stats(nums) # アンパック
print(f"個数={n}, 合計={s}, 平均={avg}")
# タプルのまま受け取る
result = stats([1, 2])
print("result =", result)
# 一部だけ使う場合(慣習的に使わない変数名は_にする)
_, total_only, _ = stats([5, 5, 5])
print("total_only =", total_only)
個数=3, 合計=60, 平均=20.0
result = (2, 3, 1.5)
total_only = 15
値の個数が合わない時の注意
アンパックの個数が合わないと例外(ValueError)になります。
個数を合わせるか、余りを*
で受けるか、タプルのまま受けるのが対策です。
# 個数・合計・平均を一度に返す関数
def stats(xs):
count = len(xs)
total = sum(xs)
avg = total / count if count else None
return count, total, avg # タプル(複数値)で返す
# 3つ返るのに2変数で受け取ろうとして失敗
try:
a, b = stats([1])
except ValueError as e:
print("アンパック失敗:", e)
# 余りは*で受け取る(拡張アンパック)
first, *rest = stats([1])
print("first =", first, "rest =", rest)
# そもそも1変数で受け取る
t = stats([1])
print("タプルt =", t)
アンパック失敗: too many values to unpack (expected 2)
first = 1 rest = [1, 1.0]
タプルt = (1, 1, 1.0)
戻り値のコツと注意点(Python初心者)
早期returnで分岐をシンプルに
複雑な入れ子のif
を避け、満たさない条件を先に弾く「ガード節」にすると読みやすくなります。
# 入れ子が深い例(非推奨)
def price_with_nested(price, coupon):
if price >= 0:
if coupon is not None:
price = price - coupon
return max(price, 0)
else:
return price
else:
return 0
# ガード節で早期return(推奨)
def price_with_guard(price, coupon):
if price < 0:
return 0
if coupon is None:
return price
return max(price - coupon, 0)
print(price_with_nested(1000, 300))
print(price_with_guard(1000, 300))
700
700
return後のコードは実行されない
return
の後に書いたコードは実行されません。
到達不能コードは削除しましょう。
def demo():
print("start")
return 123
print("ここには到達しません") # 実行されない
print(demo())
start
123
戻り値の型を統一する(一貫性)
同じ関数が状況によって型の異なる値を返すと、利用側での条件分岐やバグの原因になります。
基本は同じ型、未知や失敗はNone
などに統一しましょう。
# 悪い例: 戻り値の型がバラバラ
def find_user_age(name):
if name == "Alice":
return 20 # int
if name == "Bob":
return "unknown" # str(型が違う)
return None # None(さらに違う)
for n in ["Alice", "Bob", "Carol"]:
age = find_user_age(n)
print(n, "=>", age, type(age))
Alice => 20 <class 'int'>
Bob => unknown <class 'str'>
Carol => None <class 'NoneType'>
# 良い例: 未知はNone(=見つからない)に統一
def find_user_age2(name):
data = {"Alice": 20}
return data.get(name) # 未登録はNone
for n in ["Alice", "Bob", "Carol"]:
age = find_user_age2(n)
if age is None:
print(n, "=> age不明")
else:
print(n, "=>", age)
Alice => 20
Bob => age不明
Carol => age不明
エラー時の戻り値(Noneや特別な値)
初心者が扱いやすいのは失敗時にNone
を返す方法です。
呼び出し側はis None
で判定します。
状況によっては(成功フラグ, 値)のタプルを返すパターンも有効です。
# 失敗時にNoneを返す
def to_int(text):
try:
return int(text)
except ValueError:
return None
cases = ["42", "3.14", "abc"]
for s in cases:
v = to_int(s)
if v is None:
print(f"{s!r} は整数に変換できません")
else:
print(f"{s!r} -> {v} (type={type(v).__name__})")
'42' -> 42 (type=int)
'3.14' は整数に変換できません
'abc' は整数に変換できません
# (成功フラグ, 値)で返す
def to_int2(text):
try:
return True, int(text)
except ValueError:
return False, None
ok, value = to_int2("100")
print("ok=", ok, "value=", value)
ok, value = to_int2("oops")
print("ok=", ok, "value=", value)
ok= True value= 100
ok= False value= None
どの方式を使うかはプロジェクトの方針次第ですが、同じ関数内でルールを統一し、ドキュメント(関数のdocstringなど)に明記しておくのが大切です。
まとめ
戻り値は、関数の結果を再利用可能にするための中核的な仕組みです。
return
で値を返し、print
は表示専用という役割の違いを理解しましょう。
戻り値が無い時はNone
になり、判定はis None
を使います。
複数値はタプルで返し、アンパックで受け取れます。
実務では、早期return
で読みやすさを保ち、戻り値の型を統一し、エラー時の扱い(例: None
や(成功フラグ, 値))を決めておくと堅牢です。
小さな関数でも「何を返すか」を最初に設計することが、読みやすくテストしやすいPythonコードへの近道です。