web-dev-qa-db-fra.com

Additionnez une liste qui contient 'None' en utilisant Python

Fondamentalement, ma question est de dire que vous avez une liste contenant "Aucun", comment essayez-vous de récupérer la somme de la liste. Voici un exemple que j'ai essayé qui ne fonctionne pas et j'obtiens l'erreur: TypeError: unsupported operand type(s) for +: 'int' and 'NoneType'. Merci

def sumImport(self):
    my_list = [[1,2,3,None],[1,2,3],[1,1],[1,1,2,2]]
    k = sum(chain.from_iterable(my_list))
    return k
34
Sam

Vous pouvez utiliser la fonction filter

>>> sum(filter(None, [1,2,3,None]))
6

Mis à jour à partir des commentaires

En règle générale, filter est filter(func, iterable), mais le passage de None comme premier argument est un cas spécial, décrit dans Documents Python . Citant:

Si la fonction est None, la fonction d'identité est supposée, c'est-à-dire que tous les éléments d'itérable qui sont faux sont supprimés.

44
Alexey Kachayev

Supprimez les éléments None (et zéro) avant de sommer en utilisant filter:

>>> k = sum(filter(None, chain.from_iterable(my_list)))
>>> k
20

Pour voir pourquoi cela fonctionne, consultez la documentation pour filter :

filter(function, iterable)

Construisez une liste à partir des éléments de iterable pour lesquels function renvoie true. iterable peut être soit une séquence, un conteneur qui prend en charge l'itération, soit un itérateur. Si itérable est une chaîne ou un Tuple, le résultat a également ce type; sinon c'est toujours une liste. Si la fonction est None, la fonction d'identité est supposée, c'est-à-dire que tous les éléments d'itérable qui sont faux sont supprimés.

Notez que filter(function, iterable) est équivalent à [item for item in iterable if function(item)] si la fonction n'est pas None et [item for item in iterable if item] Si la fonction est None.

9
Mark Byers

Une autre suggestion:

from itertools import chain
k = sum(x for x in chain.from_iterable(my_list) if x)
5
Tim Pietzcker

En supposant que vous souhaitez traiter None comme zéro, une méthode simple est

sum(x if x is not None else 0 for x in chain.from_iterable(my_list))
4
BrenBarn

Vous avez toujours la possibilité d'écrire simplement la boucle que vous souhaitez:

k = 0
for sublist in my_list:
    for val in sublist:
        if val is not None:
            k += val

Mais cela ne fait certainement pas de mal non plus de connaître filter.

0
Jason Orendorff

Explicitement, cela équivaut à filtrer:

k = sum([x for x in chain.from_iterable(my_list) if x])

Cela m'évite de me souvenir d'une autre fonction. : P

0
Taro Sato