閉じる

【Python】リストの追加・変更・削除を解説(append/insert/remove/pop/del)

Pythonのリストは、学習の早い段階で必ず使う基礎データ構造です。

この記事では要素の追加(append/insert)、変更(インデックス/スライス代入)、削除(remove/pop/del)を順番に整理し、初心者の方でも迷わないように実行例と注意点を丁寧に説明します。

実務でつまずきがちな参照や例外も押さえます。

Pythonを扱う求人
読み込み中…

リストに要素を追加する(append/insert)

appendで末尾に追加

最もよく使う追加方法appendです。

リストの末尾に1要素だけを追加します。

Python
# 末尾に要素を追加する append の基本
fruits = ["apple", "banana"]
fruits.append("cherry")  # 末尾に1要素追加
print(fruits)

# append は「1つの要素」を追加する点に注意
nums = [1, 2]
nums.append([3, 4])  # リストをそのまま1要素として追加(ネストされる)
print(nums)
実行結果
['apple', 'banana', 'cherry']
[1, 2, [3, 4]]

ポイントとして、appendは配列を「展開」せず、そのものを1要素として末尾に入れます。

insertで任意の位置に追加

insert(index, value)は、指定位置に新しい要素を挿入します。

既存の要素は右へシフトします。

Python
# 任意の位置に追加する insert の基本
letters = ["a", "c", "d"]
letters.insert(1, "b")        # インデックス1の位置に'b'を挿入
print(letters)

# 先頭や末尾付近、負のインデックスの例
letters.insert(0, "start")    # 先頭に挿入
letters.insert(len(letters), "end")  # 末尾に挿入(appendと同じ結果)
letters.insert(-1, "X")       # 末尾の1つ手前に挿入
print(letters)

# 範囲外のインデックスは丸められる
nums = [10, 20]
nums.insert(100, 99)          # 末尾に追加される
nums.insert(-100, 0)          # 先頭に追加される
print(nums)
実行結果
['a', 'b', 'd', 'c']
['start', 'a', 'b', 'd', 'X', 'c', 'end']
[0, 10, 20, 99]

appendとinsertの使い分け

基本はappendで末尾に積み上げ、順番を制御したいときや途中に挟みたいときだけinsertを使います。

パフォーマンス面では、リストの途中に入れるinsertは要素のシフトを伴うため、大きなリストで頻繁に行うと遅くなる点に注意します。

末尾追記が中心ならappendが高速です。

以下に比較を簡単にまとめます。

メソッド追加位置速度の目安主用途
append(x)末尾のみ速いログや結果の順次蓄積
insert(i, x)任意の位置遅くなりやすい並び順の制御、見出しの挿入

追加時の注意点(ネスト/参照)

リストはミュータブル(変更可能)なオブジェクトで、参照が共有されることを意識する必要があります。

まず、appendでリストを追加するとネストになります。

加えて、同じインナ−リストを複数箇所で参照すると、1箇所の更新が他方にも影響します。

Python
# 同じリストオブジェクトを2回追加した場合の参照の共有
row = [0, 0]
grid = []
grid.append(row)  # 同じオブジェクトへの参照を追加
grid.append(row)  # もう一度同じ参照を追加
grid[0][0] = 1    # 片方を更新

print(grid)       # 両方が変わって見える(同じ参照だから)
print(grid[0] is grid[1])  # 参照が同一かどうか
実行結果
[[1, 0], [1, 0]]
True

意図せず共有された参照を避けるには、新しいリストを作るかコピーします。

Python
# 新しいリストオブジェクトとして追加する例
grid = []
grid.append([0, 0])          # リテラルで新規作成
grid.append([0, 0])          # それぞれ別オブジェクト
grid[0][0] = 1
print(grid)
print(grid[0] is grid[1])    # 参照は別
実行結果
[[1, 0], [0, 0]]
False

また、リストの掛け算での初期化も落とし穴です。

Python
# NG: 内側のリスト参照がすべて同じになる
grid = [[0] * 3] * 2
grid[0][0] = 1
print(grid)  # 2行とも変わる

# OK: 内側をループで個別に生成する
grid2 = [[0] * 3 for _ in range(2)]
grid2[0][0] = 1
print(grid2)
実行結果
[[1, 0, 0], [1, 0, 0]]
[[1, 0, 0], [0, 0, 0]]

リスト要素を変更する(インデックス/スライス代入)

インデックス指定で1要素を更新

単一要素の変更はlist[index] = valueで行います。

負のインデックスは末尾から数えます。

Python
# 1要素の更新
scores = [50, 60, 70]
scores[1] = 90        # 2番目を90に
scores[-1] = 100      # 末尾を100に
print(scores)
実行結果
[50, 90, 100]

スライス代入で複数要素を置換

list[start:end:step] = iterableという形で、複数の要素をまとめて置換できます。

置換先と置換元の要素数は同数でなくても良いため、リストの長さが変わることもあります。

Python
# 基本: 連続範囲を別のシーケンスで置換
nums = [0, 1, 2, 3, 4, 5]
nums[1:4] = [10, 11]         # 要素数が減る(1,2,3 -> 10,11)
print(nums)

# 連続範囲を挿入的に増やす
nums[2:2] = [20, 21, 22]     # 空のスライス位置に挿入
print(nums)

# ステップ付きスライスは要素数を一致させる必要がある
letters = list("abcdef")
letters[::2] = ["A", "B", "C"]  # 0,2,4番目を同数で置換
print(letters)
実行結果
[0, 10, 11, 4, 5]
[0, 10, 20, 21, 22, 11, 4, 5]
['A', 'b', 'B', 'd', 'C', 'f']

変更時の注意点(IndexError/型の不一致)

単一インデックスでの代入は、存在しない位置を指定するとIndexErrorになります。

スライス代入は範囲外でも空の範囲として扱われるため例外にはなりにくいですが、代入値は「イテラブル」でなければTypeErrorになります。

Python
data = [1, 2, 3]
try:
    data[5] = 99              # 範囲外: IndexError
except IndexError as e:
    print("IndexError:", e)

try:
    data[1:2] = 100           # イテラブルではない: TypeError
except TypeError as e:
    print("TypeError:", e)

# 型の不一致は文法上はOKでも、後段ロジックでバグの原因になりやすい
data[0] = "one"               # 文字列に置き換え(可)
print(data)
実行結果
IndexError: list assignment index out of range
TypeError: can only assign an iterable
['one', 2, 3]

型の一貫性は後の処理の前提になります。

特に数値リストの途中に文字列を混ぜると、合計や並べ替えでエラーになります。

混在させない設計を心がけます。

リスト要素を削除する(remove/pop/del)

removeで値を指定して削除

remove(value)最初に見つかった値だけを削除します。

該当がないとValueErrorです。

Python
colors = ["red", "blue", "green", "blue"]
colors.remove("blue")  # 最初の"blue"だけ消える
print(colors)

# 見つからないと ValueError
try:
    colors.remove("yellow")
except ValueError as e:
    print("ValueError:", e)
実行結果
['red', 'green', 'blue']
ValueError: list.remove(x): x not in list

popで位置を指定して取り出し削除

pop(index)は削除と同時に取り出した値を返すため、スタックやキューのような用途に適しています。

インデックス省略で末尾を扱います。

Python
stack = [1, 2, 3]
last = stack.pop()     # 末尾を取り出して削除
print(last, stack)

queue = ["a", "b", "c"]
first = queue.pop(0)   # 先頭を取り出して削除(計算量に注意)
print(first, queue)

# 範囲外は IndexError
try:
    queue.pop(10)
except IndexError as e:
    print("IndexError:", e)
実行結果
3 [1, 2]
a ['b', 'c']
IndexError: pop index out of range

delで位置や範囲を削除

del文は、インデックスやスライスで範囲削除できます。

戻り値はありません。

Python
nums = [0, 1, 2, 3, 4, 5, 6]
del nums[2]          # 単一要素を削除
print(nums)

del nums[1:4]        # 連続範囲を削除
print(nums)

del nums[::2]        # パターンに一致する要素を削除(ステップ指定)
print(nums)

# 変数自体の削除にも使える(以降参照するとNameError)
temp = [9, 9]
del temp
try:
    print(temp)
except NameError as e:
    print("NameError:", e)
実行結果
[0, 1, 3, 4, 5, 6]
[0, 4, 5, 6]
[4, 6]
NameError: name 'temp' is not defined

remove/pop/delの使い分け

値が分かっているならremove、位置が分かっていて取り出したいならpop、範囲でまとめて消すならdelが基本方針です。

取り出し不要で単一位置ならdel list[i]でも構いません。

以下に簡単な比較を示します。

操作指定方法戻り値主な用途例外
remove(x)なし値が分かっているときValueError
pop(i)位置(省略で末尾)取り出した値スタック/キューIndexError
del位置/範囲/ステップなし範囲削除・大量削除(構文エラー以外は通常なし)

削除時の注意点(ValueError/IndexError)

  • 値が存在するか不明な場合は、削除前にif x in list:で存在確認を行うとValueErrorを避けられます。
  • 位置で削除するときはlen(list)と比較してIndexErrorを避けます。
  • 先頭でpop(0)を多用するとシフトが頻発し遅くなるため、キュー用途ならcollections.dequeの利用を検討します。
Python
items = ["a", "b", "c"]

# 存在確認してから remove
target = "x"
if target in items:
    items.remove(target)  # 実行されない
print(items)

# 安全な pop 例
idx = 2
if 0 <= idx < len(items):
    got = items.pop(idx)
    print("popped:", got)
実行結果
['a', 'b', 'c']
popped: c

まとめ

本記事では、追加(append/insert)、変更(インデックス/スライス代入)、削除(remove/pop/del)の基本と注意点を体系的に解説しました。

末尾中心ならappend、途中に入れるならinsert、1点更新はインデックス代入、複数置換はスライス代入が有効です。

削除はremovepopdelを用途で使い分け、ValueError/IndexErrorを予防するチェックを挟むと安全です。

さらに、リストは参照型であるためネストやコピーの扱いに注意しましょう。

これらの基礎を正しく押さえることで、実用的なデータ処理がスムーズに行えるようになります。

Pythonを扱う求人
読み込み中…

クラウドSSLサイトシールは安心の証です。

URLをコピーしました!