我正在尝试对opencv cv2图像进行多色阈值处理。我要解决的问题如下:
例如
然后,如果像素具有以下任何值(RGB顺序)
它将转换为(0,0,0),否则将转换为(255,255,255)
目前,我正在使用嵌套的for循环进行此操作:
for x in range(width):
for y in range(height):
imcv[y, x] = threshold(imcv[y, x])
其中
threshold
函数执行上述逻辑。请注意,尽管我是就地完成的,但并不需要就地转换。我当前使用的方法有效,但是非常慢。我相信OpenCV / Numpy中必须有更好的方法。我对这两个框架都很陌生,不知道如何做。
我研究了OpenCV阈值功能,似乎它们只能在单通道灰度图像上工作,而且范围必须是连续范围。我需要的是对所有3个通道的离散值进行阈值处理。我想需要传递一个自定义函数,但是我无法在他们的文档中找到合适的API。
我还查找了可能可以使用的numpy API,例如
ufunc
。似乎我无法使用它来实现我想要的功能,或者我没有看到如何使用它。任何帮助表示赞赏。
编辑:
归功于AbidRahmanK和HYRY,这两种解决方案的性能均提高了x1500以上。
ncalls tottime percall cumtime percall filename:lineno(function)
1 1.576 1.576 1.576 1.576 test.py:48(preprocess_cv2_image)
1 0.000 0.000 0.001 0.001 test.py:79(preprocess_cv2_image3)
1 0.000 0.000 0.001 0.001 test.py:66(preprocess_cv2_image2)
最佳答案
请尝试以下方法:
z1 = np.dstack([np.in1d(img[...,0],B),np.in1d(img[...,1],G),np.in1d(img[...,2],R)]).reshape(img.shape)
q = np.all(z1,axis=2)
out = np.uint8(q)*255
如果该元素位于b中,
np.in1d(a,b)
将为您提供一个与True
长度相同的 bool(boolean) 数组,否则为False
。它只是Python中in
方法的向量化对应物。或简而言之:您可以对所有通道执行此操作,即检查第一个通道中B中的有效值,第二个中G并第三个中R。
然后使用
np.dstack
将它们沿z方向堆叠。为什么选择z方向?因为我们要使用 BGR-BGR-BGR ... 格式。但是请记住,这是一维数组,因此我们使用
X.reshape(img.shape)
方法将其整形为原始图像形状。因此,现在您有了一个 bool(boolean) 掩码,如果有效,则为True,否则为False。
一切都在代码的第一行。
现在,您要查看有效的BGR组合。如果所有B,G,R分量均为True,则组合有效。因此,您在z方向上应用了np.all()。再次,您得到 bool(boolean) 面罩q
q将是一个 bool(boolean) 掩码,其有效颜色为True,其他颜色为False。
因此您将转换为整数数据类型,True-> 1和False-> 0
然后将其乘以255。如果要反转图像,则可以使用
np.bitwise_not
关于python - OpenCV多色阈值,我们在Stack Overflow上找到一个类似的问题:https://stackoverflow.com/questions/21843513/