3

ここにいくつかのリストがあります:a、bなど、それぞれにいくつかの変更を加えたいのですが、forループの動作と混同しています。

例:もしそうなら

a, b = range(5), range(5,10)
for x in [a, b]: x += [0]
print(a,b)

我々が得る

([0, 1, 2, 3, 4, 0], [5, 6, 7, 8, 9, 0])

a、b が変更されます。

しかし、もしそうなら

a, b = range(5), range(5,10)
for x in [a, b]: x = x + [0]
print(a,b)

我々が得る

([0, 1, 2, 3, 4], [5, 6, 7, 8, 9])

a、b は変更されません。私は混乱しています、x と a の関係は何ですか? x を使用して a の値をいつ、またはどのように変更できますか? ところで、a+=b と a=a+b の違いは何ですか?

とにかく、私たちはこのようにできる解決策を見つけます

a, b = range(5), range(5,10)
lis = [a, b]
for i, x in enumerate(lis): 
    lis[i] = ...

次に、a と b の値を変更できます。ただし、このメソッドは追加のリストを作成する必要があります。

そして、葯の解決策があります

for x in ['a', 'b']:
    exec(x + '=' + x + '+ ...')

そして、より簡単な解決策

a, b = range(5), range(5,10)
for x in [a, b]: x[:] = x + [0]
print(a,b)

a、bが変更されていることがわかります:)

4

2 に答える 2

7

この関係は、Python のすべての変数バインディングと同じです。名前は値にバインドされます。表示されている違いは、異なることを行っているためです。値を操作している場合もあれば、名前を操作している場合もあります。

リストの場合+=、リストをその場で拡張します。つまり、元のリストを変更します。したがって、リストが使用されているすべての場所で変更が表示されます。

を実行すると、名前を新しいリスト (古いリストに を追加して形成)x = x + [0]に再バインドします。これは元のリストを変更しないため、そのリストを使用する他の場所には変更が表示されません。x[0]

「変数」、「名前」、「値」、「参照による呼び出し」などに関する Python の質問を検索すると、これに関する他の議論が見つかります。 これは、関数とパラメーターのバインディングのコンテキストで同様の問題を議論する質問です。原則は、for ループの変数バインドでも同じです。

于 2013-03-12T06:03:47.813 に答える
3

この線:

x += something

リストを所定の位置に変更しますが、次のことを行います。

x = x + something

xと を結合して新しいリストを作成しsomethingます。

次の簡略化されたデモンストレーションと違いはありません。

>>> a = [7]      # The object is [7], name a is connected to it.
>>> x = a        # Now name x is also connected.
>>> x += [2]     # Here we change the backing object (behind a AND x).
>>> a            # So that both names seem to change.
[7, 2]
>>> x
[7, 2]

>>> a = [7]      # The object is [7], name a is connected to it.
>>> x = a        # Now name x is also connected.
>>> x = x + [2]  # Here we create a NEW object from the old one, and connect x.
>>> a            # So a is unchanged.
[7]
>>> x            # But x IS changed.
[7, 2]

これは私が Python に慣れるのに最も苦労したことでした。名前と名前が参照するオブジェクトがまったく異なっており、しばしば驚くべき方法で動作する可能性があるという事実です。それはまた、一度ナットを外すと、その最も美しい機能の 1 つです。

私は最終的に、名前は C ポインターであり、すべてのオブジェクトはヒープ上にあると考え始めました (そこに専門知識があるため)。私は見つけたことがありませんが、それを考えるより良い方法があるかもしれません。

于 2013-03-12T06:11:02.253 に答える