在 Julia 中使用 BitArray 过滤数组的行

Use a BitArray in Julia to filter rows of an array

我想过滤矩阵的每一行 a,使每一行都包含非负值。

首先,我尝试了这个:

julia> a = [-1 2 3; 4 5 6; -5 3 4; 3 5 5]
4×3 Matrix{Int64}:
 -1  2  3
  4  5  6
 -5  3  4
  3  5  5

julia> # Desired Operation after filtering should yield 2x3 matrix, [4 5 6; 3 5 5]

julia> mask1 = a .>= 0
4×3 BitMatrix:
 0  1  1
 1  1  1
 0  1  1
 1  1  1

julia> a[mask1]
10-element Vector{Int64}:
 4
 3
 2
 5
 3
 5
 3
 6
 4
 5

第一次尝试展平了我的矩阵。当我做 a[mask1, :].

时也会发生同样的事情

我的第二次尝试我尝试了这个(等效逻辑使用 python 的 numpy):

julia> mask2 = minimum(a, dims=2) .>= 0
4×1 BitMatrix:
 0
 1
 0
 1

julia> a[mask2, :]
2×1 Matrix{Int64}:
 4
 3

当我想要整个第二行和第四行时,我的第二次尝试只捕获了第二行和第四行的第一个元素。请注意,如果我对 mask2 使用等效的布尔数组,我会得到所需的结果:

julia> mask3 = [false; true; false; true]
4-element Vector{Bool}:
 0
 1
 0
 1

julia> a[mask3, :]
2×3 Matrix{Int64}:
 4  5  6
 3  5  5

那么,执行此逐行过滤以将 BitMatrix 转换为 Vector{Bool} 的惯用方法,还是有更简洁的方法?此外,问题的症结在于为什么 BitMatrix 仅 returns 一行中的一个元素,而 Vector{Bool} returns 整行。

一种可能的方式:

julia> a[[all(row.>=0) for row in eachrow(a)], :]
2×3 Matrix{Int64}:
 4  5  6
 3  5  5

另一个:

julia> a[findall(x->all(x .>=0), eachrow(a)), :]
2×3 Matrix{Int64}:
 4  5  6
 3  5  5

您尝试使用 minimum 的版本是:

julia> a[minimum.(eachrow(a)) .>= 0, :]
2×3 Matrix{Int64}:
 4  5  6
 3  5  5

或遵循@DNF 建议,这实际上是最好的:

julia> a[all.(>=(0), eachrow(a)), :]
2×3 Matrix{Int64}:
 4  5  6
 3  5  5