【问题标题】:Find the Contour Properties查找轮廓属性
【发布时间】:2018-07-09 11:41:03
【问题描述】:

我正在使用 Visual Studio 2012 和 OpenCV。我想找到具有以下规格的两点坐标。

  1. 第一个点:最高和最左边的点。

  2. 第二点:最高和最右边的点。

就像你在图片中看到的那样。

【问题讨论】:

    标签: opencv image-processing computer-vision opencv-contour


    【解决方案1】:

    首先我想指出,这个答案是用 Python 编写的,旨在提供一个关于如何解决此类问题的想法。

    其次,定义最高点和最左点是一个问题(最高点和最右点相同),因为轮廓的形状变化很大。这意味着左右的最极端值并不总是与最高值互补。以底部图片为例:

    右上角的红点是北向最高的点,但它不是最右边的(它是所有 4 个点中最左边的),而底部的红点是最右边的点,但它不是最高的(实际上是最低的北方!)。还有另外 2 点介于两者之间,可以符合上述标准。

    话虽如此,我已经在 Python 中为您的图片中描述的最相似的解决方案制作了一个脚本,以展示我将如何尝试处理该问题。它可能不是您想要的,并且可能有更好的解决方案,但这可能会给您一个想法或明确您的实际需要。

    我冒昧地下载了您的示例图片并对其进行了一些编辑,以便制作示例。这是我的“原件”:

    我已经提取了图像的轮廓并选择了最大的一个 - 返回一个点数组。然后我提取了 X 坐标(最右点)和最低 Y 坐标(最北点)中的最大值。因为轮廓没有直线,我已经为最极端的重要点可以变化多少设置了一个阈值(在你的情况下,数字可能不同 - 我的情况 +- 3)。然后,我在一个列表中附加了阈值中所有最正确的点,并在另一个列表中附加了所有最北的点。然后对于最左边的点,从列表中选择 X 坐标最低的点,在另一个列表中选择 Y 坐标最低的点作为最右边的点。

    结果如下:

    希望对您有所帮助。干杯!

    Python 示例:

    import cv2
    import numpy as np
    
    img = cv2.imread('uplupr.png')
    gray = cv2.cvtColor(img, cv2.COLOR_BGR2GRAY)
    ret, threshold = cv2.threshold(gray,170,255,cv2.THRESH_BINARY)
    im, contours, hierarchy = cv2.findContours(threshold,cv2.RETR_TREE,cv2.CHAIN_APPROX_NONE)
    mask = np.zeros(img.shape, dtype="uint8")
    cnt = max(contours, key=cv2.contourArea)
    cv2.drawContours(mask, [cnt], -1, (255,255,255), 1)
    top_right_append = 0
    top_up_append = 1000
    point_up = []
    point_right = []
    
    for i in cnt:
        top_up = int(i[:,1])
        top_right = int(i[:, 0])
        if top_right > top_right_append:
            top_right_append = int(top_right)
        if top_up < top_up_append:
            top_up_append = int(top_up)
    
    for i in cnt:
        if int(i[:,1]) < top_up_append+3:
            up = (int(i[:,0]), int(i[:,1]))
            point_up.append(up)
    
    for i in cnt:
        if int(i[:,0]) > top_right_append-3:
            right = (int(i[:,0]), int(i[:,1]))
            point_right.append(right)
    
    point_up.sort(key=lambda tup: tup[0])
    point_right.sort(key=lambda tup: tup[1])
    
    cv2.circle(mask,(point_up[0]), 4, (0,0,255), -1)
    cv2.circle(mask,(point_right[0]), 4, (0,0,255), -1)
    
    cv2.imshow('image', mask)
    

    【讨论】:

    • 嗨。这段代码很棒。但它不能为 C++ 编写吗?如果可以请帮助
    • 对不起,我是从 Python 开始的,真的不懂 C++……但我相信翻译它并不难,因为它又小又简单
    • 谢谢,我正在努力实现它
    猜你喜欢
    • 1970-01-01
    • 2012-12-08
    • 2012-11-06
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2012-12-22
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多