リストをコピーする

Pythonでリストをコピーしようとして別の変数に代入すると、アレッという状況に陥ります。Pythonのドキュメントには下記のような記載があります。

目次

  1. 代入ではオブジェクトはコピーされない
  2. リストをcopyメソッドでコピーする
  3. スライスでリストのコピーを作る
  4. listコンストラクタでリストのコピーを作る
  5. 浅いコピーと深いコピー
Python において代入文はオブジェクトをコピーしません。代入はターゲットとオブジェクトの間に束縛を作ります。

つまり、代入は「参照を渡す」というような感じなのでしょうか。

代入ではオブジェクトはコピーされない

ちょっと試してみます。

>>> original = ['a','b','c']
>>> assignment = original
>>> original
['a', 'b', 'c']
>>> assignment
['a', 'b', 'c']

>>> assignment[2] = 'd'
>>> original
['a', 'b', 'd']
>>> assignment
['a', 'b', 'd']

originalというリストをassignmentという変数に代入して、そのassignmentを変更したら、originalまで変わってしまいました。

これはこれで使い方によっては便利なのかもしれませんが、単純にコピーが欲しい場合があります。

リストをcopyメソッドでコピーする

copyメソッドを使うと、リストの浅いコピー(shallow copy)を作れます。

list = L.copy()
変数 内容
L コピー元のリスト
list Lの浅いコピー

試してみます。

originalというリストを、代入した場合(assignment)と、copyした場合(copied)を比べてみます。

>>> original
['a', 'b', 'd']
>>> assignment = original
>>> copied = original.copy()

>>> original
['a', 'b', 'd']
>>> assignment
['a', 'b', 'd']
>>> copied
['a', 'b', 'd']

>>> assignment[2] = 'e'
>>> original
['a', 'b', 'e']
>>> assignment
['a', 'b', 'e']
>>> copied
['a', 'b', 'd']

代入で作ったリストを変更するとオリジナルも変更されます。ですが、copyメソッドで作ったリストは変更されません。

スライスでリストのコピーを作る

スライスでリストの浅いコピーを作ってみます。

list = L[:]
変数 内容
L コピー元のリスト
list Lの浅いコピー
>>> original
['a', 'b', 'e']
>>> assignment = original
>>> sliced = original[:]

>>> original
['a', 'b', 'e']
>>> assignment
['a', 'b', 'e']
>>> sliced
['a', 'b', 'e']

>>> assignment[2] = 'f'
>>> original
['a', 'b', 'f']
>>> assignment
['a', 'b', 'f']
>>> sliced
['a', 'b', 'e']

オリジナルが変わっても、スライスで作ったコピーは変わりませんね。

listコンストラクタでリストのコピーを作る

listクラスのコンストラクタを使って、浅いコピーが作れます。

copied = list(original)
変数 内容
original コピー元のリスト
copied originalの浅いコピー

試してみます。

>>> original = ['a','b','c']
>>> assignment = original
>>> constructed = list(original)

>>> original
['a', 'b', 'c']
>>> assignment
['a', 'b', 'c']
>>> constructed
['a', 'b', 'c']

>>> assignment[2] = 'f'

>>> original
['a', 'b', 'f']
>>> assignment
['a', 'b', 'f']
>>> constructed
['a', 'b', 'c']

コンストラクタでコピーしたリストは、オリジナルの変更の影響を受けてませんね。

浅いコピーと深いコピー

浅いコピー(shallow copy)があれば深いコピー(deep copy)もあります。

オブジェクトを含むオブジェクトをコピーするときに、どちらを使うか選びます。

広告

Pythonのデータカテゴリの投稿