4.

Python リスト要素の更新方法(インデックス代入 / スライス代入 / 一括更新 / イミュータブルとの違い)

編集
この記事の要点
  • Python のリストはミュータブル — 作成後に要素を更新できる
  • 基本構文: list[index] = 新しい値 — インデックス指定で 1 要素を上書き
  • スライス代入: list[1:3] = [...]複数要素を一気に更新 / 個数変更も可
  • 負のインデックスで末尾から: list[-1] = ... は最後の要素
  • 存在しないインデックスへの代入は IndexError — 拡張には append()insert() を使う

Python のリスト要素更新とは

Python の listミュータブル (変更可能) なシーケンスで、作成後に個々の要素を上書きできます。タプルや文字列がイミュータブル (変更不可) なのと対照的です。

基本構文 — インデックス代入

list1 = ["a", "b", "c"]
list1[1] = "B"
print(list1)
# 出力: ['a', 'B', 'c']

負のインデックス

負のインデックスは末尾から数えた位置を指します。リスト長を取得しなくても最後の要素を更新できて便利。

fruits = ["apple", "banana", "cherry"]
fruits[-1] = "grape"
print(fruits)
# 出力: ['apple', 'banana', 'grape']

fruits[-2] = "blueberry"
print(fruits)
# 出力: ['apple', 'blueberry', 'grape']

スライス代入 — 複数要素を一気に更新

list[start:stop] = iterable という構文で連続した複数要素を置き換えられます。元の範囲と新しい要素数が違っていても OKで、リスト全体の長さが自動調整されます。

nums = [1, 2, 3, 4, 5]

# 同数で置換
nums[1:3] = [20, 30]
print(nums)
# 出力: [1, 20, 30, 4, 5]

# 多い要素で置換 -> 長さが増える
nums = [1, 2, 3, 4, 5]
nums[1:3] = [20, 30, 40, 50]
print(nums)
# 出力: [1, 20, 30, 40, 50, 4, 5]

# 少ない要素で置換 -> 長さが減る
nums = [1, 2, 3, 4, 5]
nums[1:3] = [99]
print(nums)
# 出力: [1, 99, 4, 5]

# 空リストで置換 -> 削除と同じ
nums = [1, 2, 3, 4, 5]
nums[1:3] = []
print(nums)
# 出力: [1, 4, 5]

ステップ付きスライス代入

list[start:stop:step] の代入では要素数を一致させる必要があります (個数変更不可)。

nums = [1, 2, 3, 4, 5, 6]

# 偶数番目だけ更新
nums[::2] = [10, 30, 50]
print(nums)
# 出力: [10, 2, 30, 4, 50, 6]

# 要素数が合わないと ValueError
# nums[::2] = [10, 20]   # NG

IndexError — 存在しないインデックスへの代入

リスト長を超えるインデックスに直接代入することはできません。拡張するには append()insert() を使います。

list1 = ["a", "b", "c"]

# NG: IndexError
# list1[5] = "x"

# 末尾に追加
list1.append("d")
print(list1)
# 出力: ['a', 'b', 'c', 'd']

# 任意位置に挿入
list1.insert(1, "X")
print(list1)
# 出力: ['a', 'X', 'b', 'c', 'd']

関連メソッド一覧

操作方法
1 要素を更新list[i] = value
複数要素を更新list[i:j] = [...]
末尾に追加list.append(value)
位置に挿入list.insert(i, value)
リストを連結list.extend([...]) または list[len(list):] = [...]
1 要素削除del list[i] または list.pop(i)
範囲削除del list[i:j] または list[i:j] = []
値で削除list.remove(value)
全要素を更新内包表記 list = [f(x) for x in list]

リスト内包表記での一括更新

すべての要素を一定のルールで変換したい場合はリスト内包表記が Python らしい書き方。

# 全要素を 2 倍にする (新しいリスト)
nums = [1, 2, 3, 4, 5]
doubled = [n * 2 for n in nums]
print(doubled)   # [2, 4, 6, 8, 10]

# 元のリストを更新したいなら
nums[:] = [n * 2 for n in nums]
print(nums)      # [2, 4, 6, 8, 10]

# 条件付き更新
nums[:] = [n if n > 0 else 0 for n in nums]

注意 — リストのコピーと参照

リストは参照型です。代入は参照のコピーであり、片方を更新すると両方に反映されます。

a = [1, 2, 3]
b = a            # 参照を共有
b[0] = 99
print(a)         # [99, 2, 3]  <- a も変わる!

# 真のコピーを作る
c = a.copy()     # または a[:] や list(a)
c[0] = 0
print(a)         # [99, 2, 3]  <- a は変わらない

多次元リストの更新

matrix = [
    [1, 2, 3],
    [4, 5, 6],
    [7, 8, 9],
]

# 単一要素の更新
matrix[1][2] = 60
print(matrix[1])   # [4, 5, 60]

# 行全体を更新
matrix[0] = [10, 20, 30]
print(matrix[0])   # [10, 20, 30]

# 列を更新 (内包表記)
for row in matrix:
    row[0] = 0

FAQ

Q: タプルの要素は更新できる?
A: 不可。タプルはイミュータブル。更新したいなら新しいタプルを作る、もしくはリストを使う。

Q: 文字列の特定文字を更新したい
A: 文字列もイミュータブルなので不可。list(s) でリスト化して更新し ''.join(...) で戻す、または f-string / slice で組み立てる。

Q: 大量更新で速い書き方は?
A: 通常用途では内包表記で十分。数値計算なら numpy.array を使うとベクトル演算で桁違いに高速。

関連

  • 要素の数を確認 (Java の同類記事)
  • リストへの要素追加 (append / insert / extend)
  • リスト要素の削除 (del / pop / remove)
  • リスト内包表記 (List Comprehension)
編集
Post Share
子ページ

子ページはありません

同階層のページ
  1. リストの作成
  2. 要素の参照
  3. リストへの要素追加(append / extend / insert / += / slice 代入)
  4. リスト要素の更新
  5. 要素の削除
  6. リスト要素数の取得

最近更新/作成されたページ