处理布尔数组
可对布尔数组执行很多有用运算。 我们将处理之前创建的二维数组 two_dim_array。
print(two_dim_array)
输出为:
[[5 0 3 3]
[7 9 3 5]
[2 4 7 6]]
计算条目数
若要计算布尔数组中 True 条目的数量,请使用 np.count_nonzero:
有多少值小于 6?
np.count_nonzero(two_dim_array < 6)
输出为:
8
我们看到有 8 个数组条目小于 6。 获取此信息的另一种方法是使用 np.sum。 在这种情况下,False 被解释为 0,True 被解释为 1:
np.sum(two_dim_array < 5)
输出为:
6
sum() 的优点在于,与其他 NumPy 聚合函数一样,这种求和也可以沿行或列进行:
每行中有多少值小于 5?
np.sum(two_dim_array < 5, axis=1)
输出为:
array([3, 1, 2])
此代码计算矩阵每行中小于 5 的值数。
如果需要快速检查是否有任何值或所有值为 True,可使用(你猜对了)np.any 或 np.all:
有小于零的值吗?
np.any(two_dim_array < 0)
输出为:
False
亲自试一试
现在检查是否所有值都小于 10。
提示 (展开以显示)
np.all(two_dim_array < 10)
输出为:
True
还可以沿特定轴使用 np.all 和 np.any。 例如:
每行中的所有值是否都小于 7?
np.all(two_dim_array < 7, axis=1)
输出为:
array([ True, False, False])
此处,第一行和第三行中的所有元素都小于 7,但第二行并非如此。
提示
Python 具有内置的 sum()、any() 和 all() 函数。 这些函数的语法与 NumPy 版本的语法不同。 特别是在多维数组上使用时,它们会失败或产生意外的结果。 请确保对这些示例使用 np.sum()、np.any() 和 np.all()。
布尔运算符
我们已经知道如何计算降雨量小于 4 英寸的所有月份,或降雨量大于 2 英寸的所有月份。 但如果想要知道降雨量小于 4 英寸且大于 1 英寸的所有月份,该怎么办? 我们可以使用 Python 的位逻辑运算符来计算:、&、| 和 ^。 与标准算术运算符一样,NumPy 将这些运算符重载为 ufuncs,以在(通常为布尔)数组上按元素处理。
例如,我们可以按如下所示处理此类复杂问题:
np.sum((rainfall_2003 > 0.5) & (rainfall_2003 < 1))
输出为:
2
所以,我们看到有两个月的降雨量介于 0.5 英寸和 1.0 英寸之间。 此处的括号很重要。 由于运算符优先规则,删除括号后,此表达式的计算结果如下,可能会出错:
rainfall_2003 > (0.5 & rainfall_2003) < 1
输出为:
---------------------------------------------------------------------------
TypeError Traceback (most recent call last)
<ipython-input-215-4dddd2f98919> in <module>
----> 1 rainfall_2003 > (0.5 & rainfall_2003) < 1
TypeError: ufunc 'bitwise_and' not supported for the input types, and the inputs could not be safely coerced to any supported types according to the casting rule ''safe''
基于 A AND B 和 NOT (NOT A OR NOT B) 的等效性(如果你上过逻辑导论课程,可能会记得这一点),我们可以采用不同方式来计算相同结果:
np.sum(~((rainfall_2003 <= 0.5) | (rainfall_2003 >= 1)))
输出为:
2
在数组上结合使用比较运算符和布尔运算符可能产生各种高效的逻辑运算。
下表汇总了位布尔运算符及其等效的 ufuncs:
| 运算符 | 等效 ufunc |
|---|---|
& |
np.bitwise_and |
| |
np.bitwise_or |
^ |
np.bitwise_xor |
~ |
np.bitwise_not |
借助这些工具,你可以开始回答我们前面提到的关于西雅图降雨量数据的问题类型。 下面是我们将掩码与聚合组合时可以计算的一些结果示例:
print("Number of months without rain:", np.sum(rainfall_2003 == 0))
print("Number of months with rain: ", np.sum(rainfall_2003 != 0))
print("Months with more than 1 inch: ", np.sum(rainfall_2003 > 1))
print("Rainy months with < 1 inch: ", np.sum((rainfall_2003 > 0) &
(rainfall_2003 < 1)))
输出为:
Number of months without rain: 0
Number of months with rain: 12
Months with more than 1 inch: 7
Rainy months with < 1 inch: 5