2017-10-17 8 views
2

Je suis tombé sur quelques articles et sur des discussions sur StackOverflow où il est généralement recommandé d'utiliser la compréhension de listes en traitant des listes.pourquoi ne pas toujours utiliser la carte si elle est plus rapide que le reste (compréhension de la liste, boucle (variantes))?

Je rencontre généralement une structure de boucle commune où j'ai une liste et je dois la traiter et stocker les résultats dans une nouvelle liste.

donc quelque chose comme (Pour l'amour d'un exemple):

1) créer une grande liste de chaînes pour jouer autour de fin

from random import choice 
from string import ascii_uppercase 
import time 

oldlist = ([''.join(choice(ascii_uppercase) 
        for i in range(10)) for x in range(1000000)]) 
processus

2), il boucle à l'aide, la compréhension de la liste, et Les cartes de variante de la boucle 1:

start_time = time.time() 
newlist = [] 
for word in oldlist: 
    newlist.append(word.lower()) 
print(time.time()-start_time) # 0.1368732452392578 
variante de boucle

2:

start_time = time.time() 
newlist = [] 
append = newlist.append 
for word in oldlist: 
    append(word.lower()) 
print(time.time()-start_time)# 0.1112520694732666 

Liste comp:

start_time = time.time() 
newlist = [word.lower() for word in oldlist] 
print(time.time()-start_time) # 0.07511067390441895 

Carte:

start_time = time.time() 
newlist = map(str.lower, oldlist) 
print(time.time()-start_time) # 3.0994415283203125e-06 

Puis-je supposer que dans ce plan de situation devrait toujours être utilisé comme plus rapide que le reste? La compréhension de la liste est considérée plus lisible selon divers articles, mais la lisibilité devrait-elle être la première priorité ou une quantité significative de vitesse?

Note: Je viens de prendre une moyenne de cinq itérations donc ces valeurs de temps peuvent changer un peu. Cependant, cela nous donne une indication. Version Python: 3

+0

@MaximeLorant Je pense que l'un est plus générique. J'ai une situation spécifique dont je parle. – utengr

+1

Vous devez utiliser le module 'timeit' pour ces tests. –

+2

'map (str.lower, oldlist)' ne renvoie pas une liste donc ce n'est pas une comparaison équitable. Si vous ajoutez l'appel de liste, il en va de même pour les deux. Et considérant que cette carte applique une fonction à chaque élément d'un itérable, chaque comparaison de compréhension de carte/liste est aussi spécifique que celle-ci. – ayhan

Répondre

2

La performance n'est pas toujours la première priorité lors de l'écriture de code. Dans beaucoup de cas, nous pourrions ne pas nous soucier des μs perdus dans la compréhension de la liste, si cela aide à lire et à maintenir le code plus tard. Je crois que la compréhension de la liste est plus facile à lire et à comprendre que map, malgré les faibles performances perdues. EDIT, comme décrit dans les commentaires, votre exemple est biaisé puisque map renvoie un générateur, donc il ne génère rien jusqu'à ce qu'il soit répété, alors que la compréhension de la liste calcule toute la liste lors de la déclaration.

+0

pouvez-vous ajouter l'explication du commentaire ayhanś à votre réponse afin que je puisse l'accepter comme une réponse. Je recevais des résultats différents parce que je ne l'ai pas comparé de manière équitable. – utengr

+0

@engr_s Je peux, mais puisque ce n'était pas mon point (je parlais en général, et dans Py3, la carte produit un générateur en effet), ce serait juste voler une réponse :) –

+0

Je sais mais Ayhan l'a utilisé dans le commentaire il peut être bien avec :) Je pensais que c'est plus lisible pour les autres de voir mon erreur dans la comparaison si elle est mentionnée dans l'une des réponses que dans un commentaire.Si Ayhan l'ajoute comme réponse séparée, je l'accepterai volontiers. – utengr