Comment fonctionne exactement la fonction python any ()?


113

Dans la page de documentation python pour any, le code équivalent pour la any()fonction est donné comme suit:

def any(iterable):
    for element in iterable:
        if element:
            return True
    return False

Comment cette fonction sait-elle quel élément je veux tester si je l'appelle sous cette forme?

any(x > 0 for x in list)

À partir de la définition de la fonction, tout ce que je peux voir, c'est que je passe un objet itérable. Comment la forboucle sait-elle que je cherche quelque chose > 0?

Réponses:


166

Si vous utilisez, any(lst)vous voyez que lstc'est l'itérable, qui est une liste de certains éléments. S'il contenait [0, False, '', 0.0, [], {}, None](qui ont tous des valeurs booléennes de False), alors le any(lst)serait False. S'il lstcontenait également l'un des éléments suivants [-1, True, "X", 0.00001](dont tous évalués à True), alors le any(lst)serait True.

Dans le code que vous avez publié, x > 0 for x in lstil s'agit d'un autre type d'itérable, appelé expression de générateur . Avant expressions du générateur ont été ajoutées à Python, vous avez créé une compréhension de la liste , ce qui est très similaire, mais avec autour []de: [x > 0 for x in lst]. De la lstcontenant [-1, -2, 10, -4, 20], vous obtiendrez cette liste compris : [False, False, True, False, True]. Cette valeur interne serait ensuite transmise à la anyfonction, qui retournerait True, car il y a au moins une Truevaleur.

Mais avec les expressions génératrices , Python n'a plus à créer cette liste interne de True(s)et False(s), les valeurs seront générées au fur et à mesure que la anyfonction parcourt les valeurs générées une par une par l'expression du générateur. Et , depuis les anycourts-circuits, il arrêtera d'itérer dès qu'il verra la première Truevaleur. Ce serait particulièrement pratique si vous avez créé en lstutilisant quelque chose comme lst = range(-1,int(1e9))(ou xrangesi vous utilisez Python2.x ). Même si cette expression générera plus d'un milliard d'entrées, elle anyn'a qu'à aller jusqu'à la troisième entrée lorsqu'elle arrive 1, qui évalue Truepour x>0, et anypeut donc revenir True.

Si vous aviez créé une compréhension de liste , Python aurait d'abord dû créer la liste d'un milliard d'éléments en mémoire, puis la transmettre à any. Mais en utilisant une expression de générateur , vous pouvez avoir des fonctions intégrées de Python comme anyet allse déclencher tôt, dès qu'une valeur Trueou Falseest vue.


25
Il serait également intéressant de mentionner que ce any(x > 0 for x in list)n'est qu'un sucre syntaxique pour any((x > 0 for x in list)).
georg

3
Vous devriez ajouter Noneà la liste des éléments qui ont des valeurs booléennes deFalse
Alok Mysore

2
En ajoutant à @georg, le sucre syntaxique n'est pas spécial pour any. def b(x): return x; print b(x > 1 for x in xs) # prints <generator object ..
industryworker3595112

@georg Merci pour cette clarification. C'est un point vraiment important qui m'a confus lors du test du code avec des crochets.
MasayoMusic

39
>>> names = ['King', 'Queen', 'Joker']
>>> any(n in 'King and john' for n in names)
True

>>> all(n in 'King and Queen' for n in names)
False

Il suffit de réduire plusieurs lignes de code en une seule. Vous n'avez pas besoin d'écrire du code long comme:

for n in names:
    if n in 'King and john':
       print True
    else:
       print False

23

(x > 0 for x in list) dans cette fonction, l'appel crée une expression de générateur, par exemple.

>>> nums = [1, 2, -1, 9, -5]
>>> genexp = (x > 0 for x in nums)
>>> for x in genexp:
        print x


True
True
False
True
False

Qui anyutilise et court-circuite à la rencontre du premier objet qui évalueTrue


7

C'est parce que l'itérable est

(x > 0 for x in list)

Notez que x > 0retourne soit Trueou Falseet donc vous avez un itérable de booléens.


7

Dire simplement, any () fait ce travail: selon la condition, même s'il rencontre une valeur satisfaisante dans la liste, il retourne true, sinon il retourne false.

list = [2,-3,-4,5,6]

a = any(x>0 for x in lst)

print a:
True


list = [2,3,4,5,6,7]

a = any(x<0 for x in lst)

print a:
False
En utilisant notre site, vous reconnaissez avoir lu et compris notre politique liée aux cookies et notre politique de confidentialité.
Licensed under cc by-sa 3.0 with attribution required.