两个布尔列表上的 Python AND 运算符 - 如何?

2022-01-19 00:00:00 python list boolean operator-keyword

问题描述

我有两个布尔列表,例如,

I have two boolean lists, e.g.,

x=[True,True,False,False]
y=[True,False,True,False]

我想将这些列表与预期的输出相结合:

I want to AND these lists together, with the expected output:

xy=[True,False,False,False]

我认为表达式 x and y 会起作用,但后来发现它不起作用:事实上,(x and y) != (y and x)

I thought that expression x and y would work, but came to discover that it does not: in fact, (x and y) != (y and x)

x 和 y 的输出:[True,False,True,False]

y 和 x 的输出:[True,True,False,False]

使用列表推导确实有正确的输出.呼!

Using list comprehension does have correct output. Whew!

xy = [x[i] and y[i] for i in range(len(x)]

请注意,我找不到任何参考资料告诉我 AND 运算符可以像我尝试使用 x 和 y 一样工作.但是在 Python 中进行尝试很容易.有人可以向我解释 x 和 y 发生了什么吗?

Mind you I could not find any reference that told me the AND operator would work as I tried with x and y. But it's easy to try things in Python. Can someone explain to me what is happening with x and y?

这是一个简单的测试程序:

And here is a simple test program:

import random
random.seed()
n = 10
x = [random.random() > 0.5 for i in range(n)]
y = [random.random() > 0.5 for i in range(n)]
# Next two methods look sensible, but do not work
a = x and y
z = y and x
# Next: apparently only the list comprehension method is correct
xy = [x[i] and y[i] for i in range(n)]
print 'x        : %s'%str(x)
print 'y        : %s'%str(y)
print 'x and y  : %s'%str(a)
print 'y and x  : %s'%str(z)
print '[x and y]: %s'%str(xy)


解决方案

and 只是根据它们的真值返回第一个或第二个操作数.如果第一个操作数为假,则返回,否则返回另一个操作数.

and simply returns either the first or the second operand, based on their truth value. If the first operand is considered false, it is returned, otherwise the other operand is returned.

列表在非空时被认为是true,因此两个列表都被认为是true.它们的内容在这里没有作用.

Lists are considered true when not empty, so both lists are considered true. Their contents don't play a role here.

因为两个列表都不为空,x 和 y 只是简单地返回第二个列表对象;只有当 x 为空时才会返回它:

Because both lists are not empty, x and y simply returns the second list object; only if x was empty would it be returned instead:

>>> [True, False] and ['foo', 'bar']
['foo', 'bar']
>>> [] and ['foo', 'bar']
[]

请参阅 真值测试Python 文档中的部分:

See the Truth value testing section in the Python documentation:

可以测试任何对象的真值,用于 ifwhile 条件或作为以下布尔运算的操作数.以下值被认为是错误的:

Any object can be tested for truth value, for use in an if or while condition or as operand of the Boolean operations below. The following values are considered false:

[...]

  • 任何空序列,例如,''()[].

[...]

所有其他值都被认为是真——因此许多类型的对象总是真.

All other values are considered true — so objects of many types are always true.

(强调我的)和 布尔运算部分就在它下面:

(emphasis mine), and the Boolean operations section right below that:

x 和 y
如果 x 为假,则 x,否则 y

这是一个短路操作符,所以它只在第一个参数为 True 时才计算第二个参数.

This is a short-circuit operator, so it only evaluates the second argument if the first one is True.

您确实需要明确地测试列表中包含 的值.正如您所发现的,您可以通过列表理解来做到这一点.您可以使用 zip() 函数重写它 将值配对:

You indeed need to test the values contained in the lists explicitly. You can do so with a list comprehension, as you discovered. You can rewrite it with the zip() function to pair up the values:

[a and b for a, b in zip(x, y)]

相关文章