【问题标题】:Calculate the area of the masks (in pixels) in grey scale images with python用python计算灰度图像中蒙版的面积(以像素为单位)
【发布时间】:2020-01-23 20:53:34
【问题描述】:

下面的硬币图是带有不同蒙版的灰度图像(以不同的颜色显示)。有没有办法用python计算灰度图像中每个硬币的这些掩码的面积(以像素为单位)。

硬币面具的标签

{"classes": [{"title": "coin1", "shape": "polygon", "color": "#BE5C3C", "geometry_config": {}}, {"title": "coin2", "shape": "polygon", "color": "#961D82", "geometry_config": {}}, {"title": "coin3", "shape": "polygon", "color": "#C1BB5C", "geometry_config": {}}, {"title": "coin4", "shape": "polygon", "color": "#D0021B", "geometry_config": {}}, {"title": "coin5", "shape": "polygon", "color": "#417505", "geometry_config": {}}], "tags": []}

硬币面具的注释

{"tags": [], "description": "", "objects": [{"description": "", "bitmap": null, "tags": [], "classTitle": "coin1", "points": {"exterior": [[59.0, 85.0], [65.0, 70.0], [76.0, 63.0], [89.0, 61.0], [105.0, 63.0], [116.0, 78.0], [118.0, 98.0], [103.0, 117.0], [80.0, 118.0], [61.0, 103.0]], "interior": []}}, {"description": "", "bitmap": null, "tags": [], "classTitle": "coin2", "points": {"exterior": [[103.0, 43.0], [104.0, 28.0], [118.0, 17.0], [136.0, 16.0], [151.0, 22.0], [161.0, 34.0], [159.0, 53.0], [150.0, 68.0], [127.0, 73.0], [109.0, 62.0], [105.0, 54.0]], "interior": []}}, {"description": "", "bitmap": null, "tags": [], "classTitle": "coin3", "points": {"exterior": [[112.0, 143.0], [121.0, 129.0], [148.0, 124.0], [165.0, 141.0], [166.0, 160.0], [159.0, 175.0], [138.0, 184.0], [119.0, 174.0], [112.0, 161.0]], "interior": []}}, {"description": "", "bitmap": null, "tags": [], "classTitle": "coin4", "points": {"exterior": [[44.0, 137.0], [69.0, 134.0], [81.0, 152.0], [80.0, 171.0], [64.0, 181.0], [46.0, 178.0], [37.0, 168.0], [33.0, 151.0]], "interior": []}}, {"description": "", "bitmap": null, "tags": [], "classTitle": "coin5", "points": {"exterior": [[183.0, 117.0], [189.0, 100.0], [201.0, 93.0], [220.0, 98.0], [226.0, 111.0], [223.0, 126.0], [211.0, 136.0], [194.0, 135.0]], "interior": []}}], "size": {"height": 206, "width": 244}}

【问题讨论】:

    标签: python image image-processing computer-vision mask


    【解决方案1】:

    每个标记区域的真实像素数是每个标记区域的面积估计值。

    【讨论】:

    • 是的,但是当我有很多带有很多蒙版的图像时,我怎么能得到它们?
    【解决方案2】:

    这是一种使用 OpenCV 的方法。我们使用 Otsu 的阈值来获得二值图像,这使我们得到所需的前景对象为白色,而背景为黑色。从这里我们使用cv2.countNonZero(),它返回蒙版上的白色像素数


    求白色像素的个数

    pixels = cv2.countNonZero(thresh) # OR
    # pixels = len(np.column_stack(np.where(thresh > 0)))
    

    像素 198580

    我们还可以计算像素占图像总面积的百分比

    image_area = image.shape[0] * image.shape[1]
    area_ratio = (pixels / image_area) * 100
    

    面积比24.43351838727459

    import cv2
    import numpy as np
    
    image = cv2.imread('1.png')
    gray = cv2.cvtColor(image, cv2.COLOR_BGR2GRAY)
    thresh = cv2.threshold(gray,0,255,cv2.THRESH_OTSU + cv2.THRESH_BINARY)[1]
    pixels = cv2.countNonZero(thresh)
    # pixels = len(np.column_stack(np.where(thresh > 0)))
    
    image_area = image.shape[0] * image.shape[1]
    area_ratio = (pixels / image_area) * 100
    
    print('pixels', pixels)
    print('area ratio', area_ratio)
    cv2.imshow('thresh', thresh)
    cv2.waitKey(0)
    

    如果您想获得单个硬币像素区域,那么您可以遍历每个轮廓。总面积应该一样

    import cv2
    import numpy as np
    
    image = cv2.imread('1.png')
    gray = cv2.cvtColor(image, cv2.COLOR_BGR2GRAY)
    thresh = cv2.threshold(gray,0,255,cv2.THRESH_OTSU + cv2.THRESH_BINARY)[1]
    cnts = cv2.findContours(thresh, cv2.RETR_EXTERNAL, cv2.CHAIN_APPROX_SIMPLE)
    cnts = cnts[0] if len(cnts) == 2 else cnts[1]
    total = 0
    
    for c in cnts:
        x,y,w,h = cv2.boundingRect(c)
        mask = np.zeros(image.shape, dtype=np.uint8)
        cv2.fillPoly(mask, [c], [255,255,255])
        mask = cv2.cvtColor(mask, cv2.COLOR_BGR2GRAY)
        pixels = cv2.countNonZero(mask)
        total += pixels
        cv2.putText(image, '{}'.format(pixels), (x,y - 15), cv2.FONT_HERSHEY_SIMPLEX, 0.8, (255,255,255), 2)
    
    print(total)
    cv2.imshow('thresh', thresh)
    cv2.imshow('image', image)
    cv2.waitKey(0)
    

    【讨论】:

    • 谢谢。但它会给出每个硬币的像素信息吗?
    • 像素信息是什么意思?
    • 我的意思是 coin1、coin2 .....coin5 的区域。我猜你需要带有掩码标签的 .json 文件?如果是,我刚刚用标签信息更新了问题。
    • 不需要掩码标签,您可以遍历每个轮廓然后找到每个单独的硬币区域
    • 您必须将硬币标签与其轮廓相匹配,然后将此信息写入文本文件。我不知道你怎么能匹配它。最好打开另一个问题
    猜你喜欢
    • 1970-01-01
    • 2012-07-17
    • 1970-01-01
    • 2011-11-18
    • 1970-01-01
    • 1970-01-01
    • 2021-06-26
    • 1970-01-01
    • 2020-05-15
    相关资源
    最近更新 更多