Warning: file_get_contents(/data/phpspider/zhask/data//catemap/9/opencv/3.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Opencv 如何去除内部轮廓?python_Opencv_Find_Contour_Area - Fatal编程技术网

Opencv 如何去除内部轮廓?python

Opencv 如何去除内部轮廓?python,opencv,find,contour,area,Opencv,Find,Contour,Area,我正在用cv2.findContours从卫星拍摄的照片中定位光污染区域。它们中的许多并不是完全的内部污染,我的意思是,它们内部有黑洞,不应该被认为是轮廓的一部分,也不应该是单独的轮廓,因为我只是在绘制轻度污染区域的轮廓。当我开始按大小索引轮廓时,我注意到黑洞被视为单独的轮廓 处理图像 如您所见,例如#0、#67和#64被归类为等高线区域,尽管它们不应该是等高线区域 找到我正在使用的轮廓 # Reading image image_orig = cv2.imread("india_night.

我正在用cv2.findContours从卫星拍摄的照片中定位光污染区域。它们中的许多并不是完全的内部污染,我的意思是,它们内部有黑洞,不应该被认为是轮廓的一部分,也不应该是单独的轮廓,因为我只是在绘制轻度污染区域的轮廓。当我开始按大小索引轮廓时,我注意到黑洞被视为单独的轮廓

处理图像

如您所见,例如#0、#67和#64被归类为等高线区域,尽管它们不应该是等高线区域

找到我正在使用的轮廓

# Reading image
image_orig = cv2.imread("india_night.jpg")
# Processing to make contours smoother
image_gray = cv2.cvtColor(image_orig, cv2.COLOR_BGR2GRAY)
image_blurred = cv2.GaussianBlur(image_gray, (5, 5), 0)
image_blurred = cv2.dilate(image_blurred, None)
_, image_threshold = cv2.threshold(image_blurred, 0, 255, cv2.THRESH_BINARY + cv2.THRESH_OTSU)
#sorting contours by size
_, contours, _ = cv2.findContours(image_threshold, cv2.RETR_TREE, cv2.CHAIN_APPROX_NONE)
contours = sorted(contours, key=cv2.contourArea)

我的目标是不把这些未受污染的地区归类为受污染的地区

我相信你可以通过查看等级来做到这一点。基本上,如果您通过的是cv2.RETR_树,那么与-1不同的层次结构将意味着此轮廓位于另一个轮廓内

_, contours, hierarchy  = cv2.findContours(image_gray, cv2.RETR_TREE, cv2.CHAIN_APPROX_NONE)
for i in range(len(contours)):
    if hierarchy[0,i,3] == -1:
        cv2.drawContours(image_orig, contours, i, (0, 255, 0))
这将导致仅绘制如下图所示的外部轮廓

编辑: 所以,如果需要排除形状的内部部分,该怎么办。现在,这不是最理想的解决方案,但我认为它会让您更好地了解层次结构的工作原理:


您也可以通过阅读更好地了解它的工作原理

,但如果我需要外部区域的平均亮度,该怎么办?这种方式看起来会给我外区+内区的平均亮度area@Krulg我也更新了我的答案来解决这个问题。
for i in range(len(contours)):
    if hierarchy[0, i, 3] == -1:    # this is the outer contour which we need to draw
        cv2.drawContours(image_orig, contours, i, (0, 255, 0), -1)
        if hierarchy[0, i, 2] != -1:    # if this contour has inner contours
            childrenIndex = hierarchy[0, i, 2]
            while hierarchy[0, childrenIndex, 0] != -1:  # get all children for the outer contour
                childrenIndex = hierarchy[0, childrenIndex, 0]
                # now the first inner contour is just near the outer one (from the opposite side of the line)
                # thats why we are drawing that inner contour's children
                if hierarchy[0, childrenIndex, 2] != -1:
                    cv2.drawContours(image_orig, contours, hierarchy[0, childrenIndex, 2], (0, 0, 255), -1)