7
votes

Affectation des cellules d'une matrice à 2 dimensions en python, sans engourdissement

ci-dessous est mon script, qui crée essentiellement une matrice nulle de 12x8 remplie de 0. Puis je veux le remplir, un par un. Donc, disons que la colonne 2 rangée 0 doit être 5. Comment puis-je faire ça? L'exemple ci-dessous montre comment je l'ai fait et le mauvais (pour mes besoins) de sortie: xxx


1 commentaires

Thx tout le monde! J'ai compris. Ce que je faisais était de faire une liste de la même liste que tous étaient tous des pointeurs vers la même liste. Merci également pour une bonne façon d'écrire à Python. Je suis nouveau (4 semaines) pour utiliser Python. Merci a tous!


4 Réponses :


5
votes

Chaque entrée dans list_alignmatrix est une référence à le même objet . Vous devrez créer une nouvelle Liste instance pour chaque ligne de votre matrice. Voici une illustration de ce qui se passe: xxx

Vous pouvez utiliser le ID () fonction pour confirmer que chaque entrée dans l2 est une référence au même objet: xxx

Pour effectuer de nouvelles copies de votre liste de lignes, vous pouvez réécrire votre deuxième boucle comme celle-ci: xxx

list constructeur créera des copies de list_alignmatrixrow , comme illustré par l'exemple suivant: < / p> xxx


0 commentaires

1
votes

Lorsque vous appendez list_alignmatrixrow code>, il suffit d'ajouter une référence à la liste d'origine, il y a donc une seule liste 1-D et chaque ligne de votre matrice pointe dessus. Pour créer une nouvelle liste, vous devez créer une nouvelle liste:

list_AlignMatrix.append(list(list_AlignMatrixRow))


0 commentaires

1
votes

Pour générer une telle matrice, en Python, vous devez utiliser la compensation de la liste comme celle-ci Si vous souhaitez produire une ligne avec tous les 0,

>>> list_MatrixRow=[(i==0 and 5 or 0) for i in range(12)]
>>> list_MatrixRow
[5, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0]
>>> list_Matrix=[list_MatrixRow for i in range(8)]
>>> list_MatrixRow
[5, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0]
>>> list_Matrix
[[5, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0], [5, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0], [5, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0], [5, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0], [5, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0], [5, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0], [5, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0], [5, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0]]
>>> list_Matrix[0][0]
5    


9 commentaires

Quelqu'un peut-il me dire pourquoi des votes négatifs pour ma réponse !! Je pense que cela donne simplement le résultat ce qu'il veut


Vous devez également fournir une courte explication de la raison pour laquelle vous devez le faire de cette façon (voir les autres réponses). P.s. pas mon bowvote.


Je ne bownvote pas, mais je pense que c'est clair pourquoi quelqu'un a fait: l'OP essaie de éviter chaque rangée de matrice est la même rangée identique. Voir sa note "Voici la sortie qui arrive mais je ne veux pas". Vous réutilisez list_matrixrow , qui vous rend dans le même problème que l'OP est apparu.


J'ai bowndavot, mais depuis que j'ai maintenant une réponse concurrente, j'ai supprimé le bowvote. J'ai bownvote parce que l'op ne veut "qu'un seul 5 sur la cellule [2] [0]". Vous mettez les cinq sur tous les rangées. La deuxième raison du Downvote était ce bit non idiomatic (i == 0 et 5 ou 0) . Idiomatiquement, il est 5 si je == 0 autre 0 .


DeepCopy le fera, mais il est lent, nécessite une importation et est beaucoup plus longue que matrixrow [:] ou Liste (matrixrow) . Je vais admettre que cela gère des cas imbriqués que ceux-ci ne le font pas, mais ici la copie nécessaire est peu profonde.


Pour la matrice des types d'éléments de l'élévateur, DeepCopy n'est pas efficace. mais il est plus préférable de AY lorsque nous traitons avec des objets plus élevés


DeepCopy n'est pas couramment utilisé dans cette situation. Une copie peu profonde est tout ce qui est nécessaire. Lorsque nous parlons d'une liste d'entiers, les moyens les plus courants de rendre cette copie sont avec un constructeur de liste ou avec une tranche.


@Steven Rumbalski Qu'en est-il de l'évaluation du court-circuit (i == 0 et 5 ou 0), n'est-ce pas plus rapide que "5 si je == 0"


C'est un hack. Je l'utilise pour le golf du code, mais pas autrement. En ce qui concerne la vitesse, certains tests informels révèlent que 5 si i == 0 autre 0 est légèrement plus rapide que (i == 0 et 5 ou 0) .



10
votes

Chaque rangée pointe sur le même subliste. C'est le résultat d'Ajout du même subliste à plusieurs reprises. Ainsi, lorsque vous modifiez une ligne, vous finissez par modifier les autres.

Je ferais cela: p>

matrix = []
for i in range(nrows):
    matrix.append([0] * ncols)


0 commentaires