J'essaye d'appeler une fonction pour une plage de valeurs. Cette fonction renvoie une liste. Le but est de combiner toutes les listes renvoyées dans une liste.
Voici une fonction de test qui renvoie une liste:
y = [] for x in (f(i) for i in range(5)): for a in x: y.append(a)
Voici une compréhension de liste qui fait ce que je besoin que j'ai trouvé après quelques expérimentations et beaucoup de lecture StackOverflow:
y = [a for x in (f(i) for i in range(5)) for a in x]
Cependant, je ne comprends pas pourquoi et comment cela fonctionne quand une simple boucle qui résout ce problème ressemble à ceci:
def f(i): return [chr(ord('a') + i), chr(ord('b') + i), chr(ord('c') + i)]
Quelqu'un peut-il expliquer?
Merci!
3 Réponses :
Réponse à ceci:
Cependant, je ne comprends pas pourquoi et comment ça marche (list comprehensions) quand une simple boucle qui résout ce problème ressemble à ceci (pour les boucles)
Oui, ils peuvent tous les deux fonctionner mais il y a quelques différences. Tout d'abord, avec les compréhensions de liste, vous pouvez générer une liste (car c'est la sortie) après l'avoir affectée à une variable. Alors que dans une boucle for, vous devez faire créer la liste (qu'elle soit vide ou non) si vous souhaitez utiliser append ultérieurement, effectuez une opération de mise à jour / suppression / réindexation.
Deuxièmement, simplicité . Alors que les boucles for
peuvent être utilisées dans des tâches complexes où vous devez appliquer une grande variété de fonctions, et peut-être utiliser des RNG, les compréhensions de listes sont toujours préférables lorsqu'il s'agit de traiter des listes et d'effectuer des tâches plutôt `` basiques '' opérations (bien sûr, vous pouvez commencer à les imbriquer et les transformer en quelque chose de plus complexe).
Troisièmement et enfin, vitesse . Les compréhensions de listes ont tendance à être moins performantes que les boucles for pour des tâches simples.
Des informations plus détaillées concernant listcomp et les boucles for peuvent être lues dans le didacticiel officiel de python. https://docs.python.org/3/tutorial/datastructures.html
Les compréhensions de listes imbriquées sont difficiles à lire.
Mais si vous regardez les deux expressions, vous verrez qu'elles contiennent la même logique.
Dans la compréhension de la liste, le premier a
est la partie que vous souhaitez conserver dans la liste. Il est égal à y.append (a)
dans la boucle for.
Le for x in (f (i) for i in range (5))
est le même que dans votre boucle for
Il en va de même pour la ligne suivante pour a in x
Donc for x in (f (i) for i in range (5))
crée une liste x
Donc, si nous avions déjà la liste x, nous pourrions écrire
y = [a pour a in x]
Merci. Cela a maintenant un sens. Le premier A code> est ce qui est ajouté à la liste. Et les deux
pour code> Les boucles restent dans le même ordre qu'ils auraient été dans une déclaration conditionnelle régulière.
Cela peut être une meilleure illustration, à la suite de la réponse de Bendik Knapstad:
[ a # element added to the list for x in (f(i) for i in range(5)) # outer loop for a in x # inner loop that assigns to element to be added to the list ]
Quelle est exactement votre question? Vous demandez-vous pourquoi les deux dernières implémentations produisent des résultats équivalents?
@CoryKramer, je ne comprends pas comment le lire et comment le mapper à l'implémentation basée sur la boucle.
Mais c'est littéralement la même chose que les deux premières lignes de la boucle for. Comme dans, les mêmes mots dans le même ordre. Quelle est votre confusion?
@DanielRoseman, si je démonte la compréhension, cela ne correspond pas exactement à la boucle
for
. Par exemple,(f (i) for i in range (5))
renvoie une liste de listes.x
devient une seule liste dans cette liste de listes. À quoi serta pour x
dans ce cas et comment ceta
est lié àpour a in x
à la fin de l'expression?