仅使用一个表达式的Numpy矩阵二值化

时间:2015-09-01 01:37:08

标签: python numpy

我正在寻找一种基于阈值仅使用一个表达式来对numpy N-d数组进行二值化的方法。所以我有这样的事情:

np.random.seed(0)
np.set_printoptions(precision=3)
a = np.random.rand(4, 4)
threshold, upper, lower = 0.5, 1, 0

a现在是:

array([[ 0.02 ,  0.833,  0.778,  0.87 ],
       [ 0.979,  0.799,  0.461,  0.781],
       [ 0.118,  0.64 ,  0.143,  0.945],
       [ 0.522,  0.415,  0.265,  0.774]])

现在我可以触发这两个表达式:

a[a>threshold] = upper
a[a<=threshold] = lower

实现我的目标:

array([[ 0.,  1.,  1.,  1.],
       [ 1.,  1.,  0.,  1.],
       [ 0.,  1.,  0.,  1.],
       [ 1.,  0.,  0.,  1.]])

但有没有办法只用一个表达式来做到这一点?

4 个答案:

答案 0 :(得分:27)

我们可能会考虑np.where

np.where(a>threshold, upper, lower)
Out[6]: 
array([[0, 1, 1, 1],
       [1, 1, 0, 1],
       [0, 1, 0, 1],
       [1, 0, 0, 1]])

答案 1 :(得分:5)

Numpy将每个1d数组视为向量,将2d数组视为向量序列(矩阵),将3d +数组视为通用张量。这意味着当我们执行操作时,我们正在执行矢量数学运算。所以你可以这样做:

>>> a = (a > 0.5).astype(np.int_)

例如:

>>> np.random.seed(0)
>>> np.set_printoptions(precision=3)

>>> a = np.random.rand(4, 4)

>>> a
>>> array([[ 0.549,  0.715,  0.603,  0.545],
       [ 0.424,  0.646,  0.438,  0.892],
       [ 0.964,  0.383,  0.792,  0.529],
       [ 0.568,  0.926,  0.071,  0.087]])

>>> a = (a > 0.5).astype(np.int_)  # Where the numpy magic happens.

>>> array([[1, 1, 1, 1],
           [0, 1, 0, 1],
           [1, 0, 1, 1],
           [1, 1, 0, 0]])

这里发生的事情是,您将自动遍历4x4矩阵中每行的每个元素,并对每个元素应用布尔比较。

如果&gt; 0.5返回True,否则返回False。

然后通过调用 .astype 方法并传递 np.int _ 作为参数,你告诉numpy用它们的整数表示替换所有布尔值,实际上根据您的比较值对矩阵进行二值化。

答案 2 :(得分:2)

您可以直接编写表达式,这将返回一个布尔数组,它可以简单地用作1字节无符号整数(&#34; uint8&#34;)数组,以便进一步计算:

print a > 0.5

输出

[[False  True  True  True]
 [ True  True False  True]
 [False  True False  True]
 [ True False False  True]]

在一行中,您可以使用自定义上/下值来编写,例如:

upper = 10
lower = 3
treshold = 0.5

print lower + (a>treshold) * (upper-lower)

答案 3 :(得分:2)

较短的方法是简单地将条件中的布尔矩阵乘以1或1.0,具体取决于您想要的类型。

>>> a = np.random.rand(4,4)
>>> a
array([[ 0.63227032,  0.18262573,  0.21241511,  0.95181594],
       [ 0.79215808,  0.63868395,  0.41706148,  0.9153959 ],
       [ 0.41812268,  0.70905987,  0.54946947,  0.51690887],
       [ 0.83693151,  0.10929998,  0.19219377,  0.82919761]])
>>> (a>0.5)*1
array([[1, 0, 0, 1],
       [1, 1, 0, 1],
       [0, 1, 1, 1],
       [1, 0, 0, 1]])
>>> (a>0.5)*1.0
array([[ 1.,  0.,  0.,  1.],
       [ 1.,  1.,  0.,  1.],
       [ 0.,  1.,  1.,  1.],
       [ 1.,  0.,  0.,  1.]])