我正在尝试提取输入图像的蓝色。为此,我使用命令
创建蓝色HSV颜色边界和阈值HSV图像 mask_img = cv2.inRange(hsv, lower_blue, upper_blue)
之后,我使用
在输入图像和阈值图像上使用了bitwise_and res = cv2.bitwise_and(img,img,mask = mask_img)
在哪里' img'是输入图像。这段代码我是从opencv获得的。但是我不明白为什么在bitwise_and中使用三个参数以及实际上每个参数的含义是什么意思?为什么在src1和src2上使用相同的图像?
这里还有mask关键字的用途是什么?请帮我找出答案
答案 0 :(得分:4)
"和"的操作只有当mask [i]不等于零时才会执行,否则运算的结果将为零。掩模应为单通道的白色或黑色图像。你可以看到这个链接 http://docs.opencv.org/2.4.13.2/modules/core/doc/operations_on_arrays.html?highlight=bitwise#bitwise-and
答案 1 :(得分:4)
背后的基本概念是黑色的值,它的值在OPEN_CV中为0.So black + anycolor = anycolor,因为黑色的值为0。
现在假设我们有两个图像,一个名为img1
,另一个名为img2
。
img2包含我们想要放在img1上的徽标。我们创建threshold
,然后创建img2的mask
和mask_inv
,并创建img1的roi
。
现在我们要做两件事来在img1上添加img2的标识。
我们在mask_inv
的帮助下创建了roi的背景作为img1_bg,mask_inv将有两个区域一个黑色和一个白色,在白色区域我们将放置img1部分并留下黑色 -
img1_bg = cv2.bitwise_and(roi,roi,mask = mask_inv)
在你的问题中,你直接使用了img创建的面具
res = cv2.bitwise_and(img,img,mask = mask_img)
在img2中我们需要创建徽标作为roi的前景,
img2_fg = cv2.bitwise_and(img2,img2,mask = mask)
这里我们使用了遮罩层,img2的徽标部分填充在遮罩的白色部分 现在,当我们添加两个时,我们得到一个完美的组合roi 如需完整描述和理解,请访问: OPEN CV CODE FILES AND FULL DESCRIPTION
答案 2 :(得分:2)
以下链接清楚地解释了按位操作以及每个参数的重要性。 http://opencvexamples.blogspot.com/2013/10/bitwise-and-or-xor-and-not.html
void bitwise_and(InputArray src1,InputArray src2,OutputArray dst,InputArray mask = noArray())
计算两个数组或数组和标量的每元素逐位连接。 参数: src1 - 第一个输入数组或标量。
src2 - 第二个输入数组或标量。
src - 单输入数组。
值 - 标量值。
dst - 输出数组,其大小和类型与输入数组相同。 mask - 可选操作掩码,8位单通道数组,指定要更改的输出数组的元素
答案 3 :(得分:2)
从以上答案中,我们可能知道bitwise_and()参数的定义,但它们都不能回答另一个问题
为什么在src1和src2使用相同的图像?
这个问题应该是由于OpenCV文档中的函数定义过于简化引起的,对于某些人来说可能是模棱两可的,在文档中,bitwise_and()被定义为
dst(I)= sur1(I)^ sur2(I),如果mask(I)!= 0,其中^代表'and'运算符
乍看之下,我无法获得有关mask(I)为0时如何处理dst(I)的图片。
从测试结果来看,我认为它应该给出更清晰的功能定义
dst(I)= sur1(I)^ sur2(I),如果mask(I)!= 0,
否则dst(I)保留其原始值,并且dst数组的所有元素的默认值为0。
现在我们可能知道,对于sur1和sur2使用相同的图像,它将仅将原始图像部分保留在mask(I)!= 0的区域中,而其他区域则显示dst图像的部分(因为面具形状)
对于其他按位运算,其定义应与上述相同,它们还需要添加否则条件和dst数组的默认值描述
答案 4 :(得分:2)
每个参数实际上是什么意思?
res = cv2.bitwise_and(img,img,mask = mask_img)
src1:第一个图像(用于合并的第一个对象) src2:第二张图片(用于合并的第二个对象) 遮罩:理解为合并规则。如果图像的区域(先是灰度级,然后是蒙版)是黑色(值为0),则不进行合并(将第一个图像的区域与第二个图像的区域合并)。反之亦然,它将被执行。在您的代码中,引用的图像是“ mask_img”。 就我而言,当我的代码变成白色+ anycolor = anycolor时,我的代码是正确的; 导入cv2 将numpy导入为np
# Load two images
img1 = cv2.imread('bongSung.jpg')
img2 = cv2.imread('opencv.jpg')
# I want to put logo on top-left corner, so I create a ROI
rows, cols, channels = img2.shape
roi = img1[0:rows, 0:cols]
# NOw we need to create a mask of the logo, mask is conversion to grayscale of an image
img2gray = cv2.cvtColor(img2, cv2.COLOR_BGR2GRAY)
ret, mask = cv2.threshold(img2gray, 220, 255, cv2.THRESH_BINARY_INV)
cv2.imshow('mask', mask)
mask_inv = cv2.bitwise_not(mask)
#cv2.imshow("mask_inv", mask_inv)
#When using bitwise_and() in opencv with python then white + anycolor = anycolor; black + anycolor = black
img1_bg = cv2.bitwise_and(roi,roi,mask = mask_inv)
#cv2.imshow("img1_bg", img1_bg)
cv2.imshow("img2", img2)
img2_fg = cv2.bitwise_and(img2,img2,mask = mask)
cv2.imshow('img2_fg', img2_fg)
dst = cv2.add(img1_bg,img2_fg)
img1[0:rows, 0:cols] = dst
#cv2.imshow("Image", img1)
cv2.waitKey(0)
cv2.destroyAllWindows()
答案 5 :(得分:0)
关于使用img两次,我的猜测是我们并不关心img [i]和img [i]是什么,因为它只是img [i]二进制文件。重要的是,正如Mohammed Awney所提到的,当掩码为0时,我们将img [i]设为0,否则我们将像素单独留下。根据我们的面具,这是一种使img变成黑色像素的方法。
答案 6 :(得分:0)
bitwise_and ( InputArray src1, 输入数组 src2, 输出数组 dst, InputArray 掩码 = noArray() )
src1 第一个输入数组或标量。
src2 第二个输入数组或标量。
与输入数组具有相同大小和类型的 dst 输出数组。
mask 可选操作掩码,8 位单通道数组,指定要更改的输出数组元素。
dst(I)=src1(I)∧src2(I)if mask(I)≠0
和掩码对 dst 进行操作
计算两个数组的按位连接 (dst = src1 & src2) 计算两个数组或一个数组和一个标量的每个元素的按位连接。