TL;DR
Nous commençons par résumer les deux comportement des deux opérateurs logiques and
et or
. Ces langues seront à la base de notre discussion ci-dessous.
and
De retour de la première Falsy valeur si il y en a, d'autre le retour de la dernière
la valeur de l'expression.
or
De retour de la première Truthy valeur si il y en a, d'autre le retour de la dernière
la valeur de l'expression.
Le comportement est également résumée dans les docs, surtout dans ce tableau:
Le seul opérateur en renvoyant une valeur booléenne, indépendamment de ses opérandes est l' not
de l'opérateur.
"Truthiness", et "Truthy" Évaluations
La déclaration
len(args) and max(args) - min(args)
Est un très pythonic concis (et sans doute moins lisible) façon de dire "si args
n'est pas vide, retourner le résultat d' max(args) - min(args)
", sinon retour 0
. En général, c'est une représentation concise de l' if-else
expression. Par exemple,
exp1 and exp2
Devrait (à peu près) à traduire:
r1 = exp1
if not r1:
r1 = exp2
Ou, de manière équivalente,
r1 = exp1 if exp1 else exp2
Où exp1
et exp2
sont arbitraires des objets python, ou des expressions qui renvoient un objet. La clé pour comprendre les usages de la logique and
et or
opérateurs ici est de comprendre qu'ils ne sont pas limités à l'exploitation, ou de retourner des valeurs booléennes. N'importe quel objet avec un truthiness valeur peut être testé ici. Cela inclut int
, str
, list
, dict
, tuple
, set
, NoneType
, et des objets définis par l'utilisateur. Court-circuiter les règles s'appliquent toujours ainsi.
Mais qu'est-ce que truthiness?
Il se réfère à la manière dont les objets sont évalués lorsqu'utilisé dans les expressions conditionnelles. @Patrick Haugh résume truthiness bien dans ce post.
Toutes les valeurs sont considérées comme des "truthy", sauf pour les éléments suivants, qui sont
"falsy":
None
False
0
0.0
0j
Decimal(0)
Fraction(0, 1)
-
[]
- vide list
-
{}
- vide dict
-
()
- vide tuple
-
''
- vide str
-
b''
- vide bytes
-
set()
- vide set
- un vide
range
, comme range(0)
- les objets pour lesquels
-
obj.__bool__()
retours False
-
obj.__len__()
retours 0
Un "truthy" de la valeur de satisfaire à la vérification effectuée par if
ou while
des déclarations. Nous utilisons des "truthy" et "falsy" pour se démarquer de la
bool
valeurs True
et False
.
Comment and
Travaux
Nous nous appuyons sur les OP de la question comme un enchaîner sur une discussion sur la façon dont ces opérateurs dans ces instances.
Étant donné une fonction avec la définition
def foo(*args):
...
Comment puis-je retourner la différence entre la valeur minimum et maximum
dans une liste de zéro ou plusieurs arguments?
Trouver le minimum et le maximum est facile (utilisez la fonction intégrée de fonctions!). Le seul hic ici est de manière appropriée de la manipulation de l'angle cas où l'argument de la liste peut être vide (par exemple, en appelant foo()
). Nous pouvons faire les deux en une seule ligne grâce à l' and
opérateur:
def foo(*args):
return len(args) and max(args) - min(args)
foo(1, 2, 3, 4, 5)
# 4
foo()
# 0
Depuis and
est utilisé, la seconde expression doit également être évaluée si le premier est True
. Notez que, si la première expression est évaluée à truthy, la valeur de retour est toujours le résultat de la deuxième expression. Si la première expression est évaluée à Falsy, puis le résultat retourné est le résultat de la première expression.
Dans la fonction ci-dessus, Si foo
reçoit un ou plusieurs arguments, len(args)
est plus grand que 0
(un nombre positif), de sorte que le résultat retourné est - max(args) - min(args)
. Otoh, que, si aucun argument n'est passé, len(args)
est 0
qui est Falsy, et 0
est retourné.
Notez qu'une autre façon d'écrire cette fonction serait:
def foo(*args):
if not len(args):
return 0
return max(args) - min(args)
Ou, de façon plus concise,
def foo(*args):
return 0 if not args else max(args) - min(args)
Bien sûr, aucun de ces fonctions effectuer toute vérification de type, de sorte que si vous faites totalement confiance à la, ne pas compter sur la simplicité de ces constructions.
Comment or
Travaux
J'explique le fonctionnement de l' or
dans un mode similaire avec un exemple artificiel.
Étant donné une fonction avec la définition
def foo(*args):
...
Comment voulez-vous compléter foo
de retour tous les numéros de plus de 9000
?
Nous utilisons or
de la poignée le coin le cas ici. Nous définissons foo
comme:
def foo(*args):
return [x for x in args if x > 9000] or 'No number over 9000!'
foo(9004, 1, 2, 500)
# [9004]
foo(1, 2, 3, 4)
# 'No number over 9000!'
foo
effectue une filtration sur la liste de retenir tous les numéros de plus de 9000
. S'il existe de tels chiffres, le résultat de la compréhension de liste est non-vide de la liste qui est Truthy, de sorte qu'il est retourné (court-circuit en action ici). Si il n'existe pas de tels chiffres, puis le résultat de la liste comp est - []
qui est Falsy. Ainsi, la deuxième expression est maintenant évalué (une chaîne non vide) et qu'il est retourné.
À l'aide des instructions conditionnelles, on peut ré-écrire cette fonction,
def foo(*args):
r = [x for x in args if x > 9000]
if not r:
return 'No number over 9000!'
return r
Comme précédemment, cette structure est plus souple en termes d'erreur de manipulation.