Je suis sûr que cela a été répondu quelque part, mais je ne savais pas comment le décrire.
Disons que je souhaite créer une liste contenant 3 listes vides, comme: P>
lst = [[]]*3 lst[0] = [5] lst[0].append(3)
5 Réponses :
Ma meilleure hypothèse est que l'utilisation de la multiplication dans la forme
[[]] * x code> provoque le stockage de Python pour stocker une référence à une seule cellule ...? P>
Oui. Et vous pouvez tester cela vous-même p>
xxx pré> ceci indique que les trois références font référence au même objet. Et notez que vraiment em> est parfaitement logique que cela arrive 1 sup>. Il suffit de copie les valeurs em>, et dans ce cas, les valeurs sont em> références. Et c'est pourquoi vous voyez la même référence répétée trois fois. P>
Il est intéressant de noter que si je fais p> blockQuote>
xxx pré> Puis le "lien" de la cellule 0 est cassé et je reçois
[[5,3], [], []] code>, mais
lst [1] .append (0). code> cause toujours
[[5,3], [0], [0] code>. p> blockQuote>
Vous avez changé la référence qui occupe
lst [0] code>; C'est-à-dire que vous avez attribué une nouvelle valeur em> à
lst [0] code>. Mais vous n'avez pas changé la valeur em> des autres éléments, ils se réfèrent toujours au même objet qu'ils ont mentionné. Et
lst [1] code> et
lst [2] code> se réfère toujours à la même instance, donc bien sûr ajouter un élément à
lst [1] code> Causes
LST [2] CODE> Pour voir également ce changement. P>
C'est une erreur classique que les gens font des pointeurs et des références. Voici la simple analogie. Vous avez un morceau de papier. Sur cela, vous écrivez l'adresse de la maison de quelqu'un. Vous prenez maintenant cette feuille de papier et photocopiez-la deux fois pour vous retrouver avec trois morceaux de papier avec la même adresse écrite sur eux. Maintenant, prenez le premier em> morceau de papier, griffonnez l'adresse écrite sur elle et écrivez une nouvelle adresse pour la maison de quelqu'un d'autre em>. L'adresse a-t-elle écrit sur les deux autres morceaux de changement de papier? Non, c'est exactement em> ce que votre code a fait, cependant. C'est pourquoi em> les deux autres éléments ne changent pas. En outre, imaginez que le propriétaire de la maison avec adresse qui est toujours em> sur le deuxième morceau de papier construit un garage add-on à leur maison. Maintenant, je vous demande, la maison dont l'adresse est-elle sur le morceau de papier em> dispose d'un garage add-on? Oui, c'est parce que c'est exactement em> la même maison que celui dont l'adresse est écrite sur le morceau de papier em>. Cela explique tout em> à propos de votre deuxième exemple de code. P>
1 sup>: Vous ne vous êtes pas attendu à Python d'invoquer un "Coopy Constructeur": Puke. P> BlockQuote>
+1 pour ID () code>. Cela sera utile.
Merci pour ID (x) code>, et le garage intégré est un bon exemple pour l'édition de pointeur.
Ceci est parce que la multiplication de séquence répète simplement les références. Lorsque vous écrivez [[]] * 2 code>, vous créez une nouvelle liste avec deux éléments, mais ces deux éléments sont l'objet même em> en mémoire, à savoir une liste vide. Par conséquent, un changement d'un est reflété dans l'autre. La compréhension, en revanche, crée une nouvelle liste nouvelle et indépendante em> sur chaque itération:
Je n'ai pas pensé à essayer l'opérateur "est", merci!
@Adrianwan pas de problème, heureux d'aider.
Ils référennent les mêmes listes. P>
Il y a des questions similaires ici et ici a> p>
et du FAQ : P>
"* Ne crée pas de copies, cela ne crée que des références à l'existant
objets. " p>
blockQuote>
+1 pour le lien vers les documents Python.
Vous devinez que l'utilisation de la multiplication dans la forme [[]] * x provoque la conservation d'une référence à une seule cellule. P>
Donc, vous vous retrouvez avec une liste de 3 références à la même liste. P>
Fondamentalement, ce qui se passe dans votre premier exemple, c'est qu'une liste est créée avec plusieurs références à la même liste intérieure. Voici une ventilation.
>>> c = [[], [], []] # this line creates four different lists >>> d = [ [] for _ in xrange(3) ] # so does this line >>> c[0].append(4) >>> d[0].append(5) >>> print c [[4], [], []] >>> print d [[5], [], []]
@Roadierich, mais les réponses ici ont une meilleure explication et des liens vers la documentation officielle.
@Aseembansal: alors ces réponses doivent être ajoutées à la question autre i> peut-être peut-être?
C'est définitivement un duplicata. Stackoverflow.com/ Questions / 240178 / ... et Stackoverflow.com/questions/1605024/... et Stackoverflow.com/questions 6688223 / ... et d'autres que je ne trouve pas en ce moment.
J'ai marqué les 3 questions comme des doublons.