Pythonにおける高度な反復処理:内包表記、イテレータ、生成器、および再帰の仕組み

三項演算子(条件付き式)

Pythonでは、単純なif-else構文を1行で記述する三項演算子が利用可能です。これはコードの簡潔性を高めるために頻繁に使用されます。

# 基本構文: [真の場合の値] if [条件式] else [偽の場合の値]
score = 85
result = "合格" if score >= 60 else "不合格"
print(result) # 出力: 合格

イテレータの概念

Pythonのオブジェクトは、反復処理が可能かどうかに基づいて「可反復オブジェクト(Iterable)」と「イテレータ(Iterator)」に分類されます。

1. 可反復オブジェクト (Iterable)

__iter__メソッドを持つオブジェクトを指します。文字列、リスト、辞書、タプル、集合などがこれに該当します。

# 数値型以外は基本的に可反復
msg = "Python"
items = [10, 20, 30]
data = {"key1": "val1"}

print(hasattr(msg, "__iter__"))  # True
print(hasattr(100, "__iter__"))  # False

2. イテレータ (Iterator)

__iter____next__の両方のメソッドを持つオブジェクトです。イテレータはデータの流れを保持し、呼び出されるたびに次の要素を返します。インデックスによるアクセスが困難なデータ構造でも値を順番に取得できます。

forループの内部動作

forループは内部的にiter()関数(__iter__の呼び出し)を使用してイテレータを取得し、next()関数(__next__の呼び出し)で値を一つずつ取り出します。最後にStopIteration例外をキャッチしてループを終了します。

colors = ["red", "blue", "green"]
it = iter(colors)

while True:
    try:
        val = next(it)
        print(val)
    except StopIteration:
        break

内包表記

リストや辞書を効率的に生成するための構文です。

リスト内包表記

# 0から9までの偶数の2乗リストを作成
squares = [n**2 for n in range(10) if n % 2 == 0]
print(squares) # [0, 4, 16, 36, 64]

辞書内包表記とzip関数

zip()関数は複数の可反復オブジェクトをまとめ、ペアのイテレータを返します。

keys = ["ID", "Name", "Role"]
values = [101, "Alice", "Admin"]

# zipを使用して辞書を生成
user_info = {k: v for k, v in zip(keys, values)}
print(user_info) # {'ID': 101, 'Name': 'Alice', 'Role': 'Admin'}

生成器(Generator)

生成器はイテレータの一種であり、一度にすべてのデータをメモリに展開せず、必要に応じて値を生成します。これにより、大量のデータを扱う際のメモリ節約が可能です。

yieldキーワード

関数内でyieldを使用すると、その関数はジェネレータ関数になります。returnは値を返して関数を終了しますが、yieldは値を返しつつ関数の状態を「一時停止」します。

def step_counter(start, end, step):
    current = start
    while current < end:
        yield current
        current += step

# カスタムrangeのような挙動
for num in step_counter(0, 10, 2):
    print(num) # 0, 2, 4, 6, 8

生成器式

リスト内包表記と似ていますが、角括弧 [] の代わりに丸括弧 () を使用します。リスト内包表記は即座にリストを構築しますが、生成器式はイテレータを返します。

# リスト内包表記(メモリを消費)
list_comp = [x * 2 for x in range(1000000)]

# 生成器式(メモリを節約、必要になるまで計算しない)
gen_expr = (x * 2 for x in range(1000000))
print(next(gen_expr)) # 0
print(next(gen_expr)) # 2

再帰関数

関数が自分自身を呼び出す手法を再帰と呼びます。再帰には必ず「ベースケース(終了条件)」と「再帰ステップ(規則性)」が必要です。

再帰を用いた階差数列の計算

例:最初の値が10で、次から2ずつ増加する数列のn番目の値を求める。

def get_sequence_value(n):
    # ベースケース: 1番目は10
    if n == 1:
        return 10
    # 再帰ステップ: 前の値に2を加える
    return get_sequence_value(n - 1) + 2

print(get_sequence_value(5)) # 出力: 18 (10, 12, 14, 16, 18)

再帰を使用する際は、最大再帰深度に注意し、終了条件が必ず満たされるように設計する必要があります。

タグ: Python Iterator Generator ListComprehension Recursion

5月20日 13:10 投稿