我正在使用带有一些语义分割算法的火炬来产生分割图像的二元掩模。然后我想基于该面具裁剪图像。为了清楚起见,我需要在每个像素的基础上裁剪它。这似乎是一个简单的问题,但我能想到的唯一解决方案是反转像Coco API中的/ogl/2502758/pakowacz%20-%20mile%20widziane%20panie
函数,或迭代数组中的每个像素并掩盖在一起将像素设置为黑色(如果不需要) 。我觉得有更好的方法可以做到这一点。 Lua,Python,Go或C ++中的库对我有用。有什么想法吗?
答案 0 :(得分:3)
我已经在Python中实现了这一点,假设你的输入图像和掩码可用作Mat Objects。 鉴于src1是你的图像,src1_mask是你的二进制掩码:
src1_mask=cv2.cvtColor(src1_mask,cv2.COLOR_GRAY2BGR)#change mask to a 3 channel image
mask_out=cv2.subtract(src1_mask,src1)
mask_out=cv2.subtract(src1_mask,mask_out)
现在,mask_out包含位于您定义的二进制掩码内的图像src1的一部分。
答案 1 :(得分:2)
对于其他遇到这种情况的人。我发现将火炬二进制掩码张量转换为Double
类型,然后简单地使用火炬的cmul
函数将其与每个RGB通道相乘。基本上,因为二进制掩码具有1
来代替分段像素,所以该值将保持不变。然而,如果它在分段之外,则它具有0
,当在通道上相乘时产生黑色。 Saransh的答案也很好,适用于开放式cv。
答案 2 :(得分:0)
将OpenCV .copyTo与掩码选项
一起使用http://docs.opencv.org/2.4/modules/core/doc/basic_structures.html#mat-copyto
答案 3 :(得分:0)
这是仅依赖于numpy的解决方案:
def get_segment_crop(img,tol=0, mask=None):
if mask is None:
mask = img > tol
return img[np.ix_(mask.any(1), mask.any(0))]
现在执行get_segment_crop(rgb, mask=segment_mask)
,而rgb
是形状(w,h,c)的ndarray,而segment_mask
是形状(w的布尔型ndarray(即包含True / False条目) ,h),因为w = width,h = height,c = channel。
答案 4 :(得分:-1)
您可以使用opencv中的boundingRect
函数来检索感兴趣的矩形,然后您可以将图像裁剪为该矩形。 python实现看起来像这样:
import numpy as np
import cv2
mask = np.zeros([600,600], dtype=np.uint8)
mask[200:500,200:500] = 255 # set some values to 255 to represent an actual mask
rect = cv2.boundingRect(mask) # function that computes the rectangle of interest
print(rect)
img = np.ones([600,600, 3], dtype=np.uint8) # arbitrary image
cropped_img = img[rect[0]:(rect[0]+rect[2]), rect[1]:(rect[1]+rect[3])] # crop the image to the desired rectangle
将mask
img
替换为您自己的