2017-11-05 2 views
0
def mutation(input_list): 
    list_copy = input_list[:] 
    list_copy[0] = 10 
    input_list = list_copy 

# Correctly mutates 
sample_list = [0,1,2] 
sample_copy = sample_list[:] 
sample_copy[0] = 10 
sample_list = sample_copy 
print(sample_list) 

# Incorrectly mutates 
sample_list = [0,1,2] 
mutation(sample_list) 
print(sample_list) 

コードの一番上のスニペットでは、リストのコピーを作成して修正しました。私はコピーにオリジナルを設定し、それが動作します。 私が混乱している理由は、関数の外でこのプロセスを行うのはなぜですか?しかし、関数(コードの2番目のスニペット)の中でそれを実行すると失敗します。参考のためコピー後のPythonリストの変異

、コードを返します:

[10, 1, 2] 
[0, 1, 2] 

編集:私はinput_list[0] = 10作品を呼び出すことを知っています。私は、これを私が何よりも上に示したことと何が違うのかを知りたいだけです。

+0

https://docs.python.org/3/faq/programming.html#how-do-i-write-a-function-with-output-parameters-call-by-referenceをご覧ください。 – randomir

+0

非常にお勧めの読書:https://nedbatchelder.com/text/names.html。これはあなたに必要なすべての答えを与えるはずです。 – SethMMorton

+1

[参照で変数を渡すにはどうすればいいですか?](0120-325-002) – randomir

答えて

4

と呼ばれるグローバル変数の値を変更する関数を書くことができ、input_listsample_listと同じオブジェクトを指し始めますが、後でlist_copyを指します。 sample_listは変更されていません。まだ元のオブジェクトを指しています。

機能の外で行う場合、印刷する前にsample_listを新しいオブジェクトを指すように変更します。

0

ローカル変数mutationの新しい値であるinput_listを設定するからです。

最も簡単な解決策は、引数として渡されたリストの最初の要素の値を変更している。

def mutation(input_list): 
    input_list[0] = 10 

そうでなければ、あなたがmutationsample_list

def mutation(): 
    global sample_list 
    list_copy = sample_list[:] 
    list_copy[0] = 10 
    sample_list = list_copy 
1

オブジェクトIDを表示するために組み込み関数idを使用すると、ここで役立つと思います。 2つの変数名のIDが同じ結果を与える場合、それらは同じオブジェクトを参照します。それ以外の場合はオブジェクトが異なります。上記で

>>> def mutation(input_list): 
...  print(id(input_list)) 
...  list_copy = input_list[:] 
...  print(id(list_copy)) 
...  input_list = list_copy 
...  print(id(input_list)) 
...  
>>> a = list(range(10)) 
>>> print(id(a)) 
140737233394376 
>>> mutation(a) 
140737233394376 
140737233289160 
140737233289160 

、我々が表示さinput_list = list_copy後、名前input_listは、それがもはや関数の引数として与えられたリストを参照意味しており、list_copyとしてメモリに同一の同じオブジェクトを参照すること。これは、あなたが期待する突然変異が機能しない理由です。まったく別のオブジェクトを変更しているのです。

関連する問題