使用numpy查找矩阵中全部为零的行
我有一个很大的 numpy
矩阵 M
。这个矩阵的某些行的所有元素都是零,我需要找出这些行的索引。现在我想到的简单方法是逐行遍历这个矩阵,然后检查每一行的每个元素。
有没有更好、更快的方法来用 numpy
实现这个目标呢?
4 个回答
在编程中,有时候我们会遇到一些问题,特别是在使用某些工具或库的时候。这些问题可能会让我们感到困惑,但其实大多数时候,解决这些问题的方法都在社区的讨论中。比如在StackOverflow上,很多人会分享他们的经验和解决方案。
如果你在编写代码时遇到错误,首先要做的是仔细阅读错误信息。错误信息通常会告诉你问题出在哪里,虽然有时候它们可能听起来很复杂。接着,你可以在网上搜索这个错误,看看其他人是怎么解决的。很多时候,你会发现已经有人遇到过类似的问题,并且他们分享了有效的解决办法。
记住,编程是一个不断学习的过程,遇到问题是很正常的。通过查阅资料和向社区求助,你会逐渐变得更加熟练。
a = numpy.array([[10,0],[0,0],[0,10]])
isZero = numpy.all(a == 0, axis=1)
deleteFullZero = a[~numpy.all(a== 0, axis=1)]
#isZero >> [False True False]
#deleteFullZero >> [[10 0][0,10]]
这里介绍了一种使用 np.sum
的方法,
如果你想设置一个阈值,这个方法会很有用。
a = np.array([[1.0, 1.0, 2.99],
[0.0000054, 0.00000078, 0.00000232],
[0, 0, 0],
[1, 1, 0.0],
[0.0, 0.0, 0.0]])
print(np.where(np.sum(np.abs(a), axis=1)==0)[0])
>>[2 4]
print(np.where(np.sum(np.abs(a), axis=1)<0.0001)[0])
>>[1 2 4]
使用 np.prod
来检查某一行是否至少包含一个零元素。
print(np.where(np.prod(a, axis=1)==0)[0])
>>[2 3 4]
这个被认可的答案适用于元素是 int(0)
的情况。如果你想找出所有值都是 0.0(浮点数)的行,你需要使用 np.isclose()
:
print(x)
# output
tensor([[0., 0., 0., 0., 0., 0., 0., 0., 0., 0., 0., 0., 0., 0., 0., 0., 0., 0.,
0., 0., 0.],
[0., 0., 0., 0., 0., 0., 0., 0., 0., 0., 0., 0., 0., 0., 0., 0., 0., 0.,
0., 1., 0.],
[0., 0., 0., 0., 0., 0., 0., 0., 0., 0., 0., 0., 0., 0., 0., 0., 0., 0.,
1., 0., 0.],
[0., 0., 0., 0., 0., 0., 0., 0., 0., 0., 0., 0., 0., 0., 0., 0., 0., 0.,
0., 0., 0.],
])
np.where(np.all(np.isclose(labels, 0), axis=1))
(array([ 0, 3]),)
注意:这个方法也适用于 PyTorch 张量,这在你想找到全为零的多热编码向量时非常有用。
这里有一种方法。我假设你已经用 import numpy as np
导入了numpy库。
In [20]: a
Out[20]:
array([[0, 1, 0],
[1, 0, 1],
[0, 0, 0],
[1, 1, 0],
[0, 0, 0]])
In [21]: np.where(~a.any(axis=1))[0]
Out[21]: array([2, 4])
这其实是对这个答案的一个小改动: 如何检查一个矩阵是否包含零列?
下面是具体的过程:
any
方法会返回 True,如果数组中有任何一个值是“真实”的。非零的数字被认为是 True,而 0 被认为是 False。通过使用参数 axis=1
,这个方法会应用到每一行上。对于示例中的 a
,我们可以得到:
In [32]: a.any(axis=1)
Out[32]: array([ True, True, False, True, False], dtype=bool)
所以每个值表示对应的行是否包含非零值。~
运算符是二进制的“非”或补码:
In [33]: ~a.any(axis=1)
Out[33]: array([False, False, True, False, True], dtype=bool)
(一个替代的表达式,结果是一样的,就是 (a == 0).all(axis=1)
。)
为了获取行的索引,我们使用 where
函数。它会返回参数为 True 的索引:
In [34]: np.where(~a.any(axis=1))
Out[34]: (array([2, 4]),)
注意,where
返回的是一个包含单个数组的元组。where
可以处理 n 维数组,所以它总是返回一个元组。我们需要的是那个元组中的单个数组。
In [35]: np.where(~a.any(axis=1))[0]
Out[35]: array([2, 4])