2012-03-19 15 views
9

considerare il seguente codice:comportamento diverso per la lista .__ iadd__ e la lista .__ add__

>>> x = y = [1, 2, 3, 4] 
>>> x += [4] 
>>> x 
[1, 2, 3, 4, 4] 
>>> y 
[1, 2, 3, 4, 4] 

e quindi prendere in considerazione questo:

>>> x = y = [1, 2, 3, 4] 
>>> x = x + [4] 
>>> x 
[1, 2, 3, 4, 4] 
>>> y 
[1, 2, 3, 4] 

Perché c'è una differenza questi due?

(E sì, ho provato a cercare questo).

+4

Ciò che è interessante della tua ultima affermazione, è che questa funzionalità è effettivamente spiegata nei documenti python: http://docs.python.org/reference/datamodel.html#object.__add__ (dalla ricerca di questi termini) – jdi

+3

@jdl: Sì, ammetto che l'ho ignorato. –

risposta

20

__iadd__ muta l'elenco, mentre __add__ restituisce un nuovo elenco , come dimostrato.

Un'espressione di tenta prima di chiamare __iadd__ e, in mancanza, chiama __add__ seguito da un incarico (vedere il commento di Sven per una correzione minore). Dal momento che list ha __iadd__ allora fa questa piccola magia della mutazione.

+1

Se desideri maggiori dettagli su questo comportamento esatto e altre informazioni sul perché Python è così com'è, ti consiglio caldamente [talk epiphanies python] (http://pyvideo.org/video/613/python-epiphanies) da PyCon 2012. Ti condurrà a molto "a ha!" momenti. –

+0

@S Singh se si ottiene la risposta, selezionare la risposta come risposta accettata e completare il flusso di lavoro. Altrimenti questa domanda verrà mostrata come senza risposta. – Nilesh

+1

Questa risposta è leggermente fuorviante: l'assegnazione viene sempre eseguita, indipendentemente dal fatto che sia chiamato '__iadd __()' o '__add __()'. 'list .__ iadd __()' restituisce semplicemente 'self', tuttavia, quindi l'assegnazione non ha alcun effetto se non quello di rendere il nome di destinazione locale all'ambito corrente. –

3

Il primo muta l'elenco e il secondo rebinda il nome.

Problemi correlati