You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

OpenCV findContours无法检测散点图中浅色点的问题求助

散点图浅色点轮廓检测问题及解决方案

我正尝试检测散点图中的点并获取其位置,使用OpenCV的findContours函数时,发现该函数仅能正确检测并绘制深色点的轮廓,浅色点无法被识别。

原代码

import cv2

img = cv2.imread('808.png')
imgGray = cv2.cvtColor(img, cv2.COLOR_BGR2GRAY)

# 寻找轮廓/形状
_, threshold = cv2.threshold(imgGray, 127, 255, cv2.THRESH_BINARY)
  
# 使用findContours函数
contours, _ = cv2.findContours(threshold, cv2.RETR_TREE, cv2.CHAIN_APPROX_NONE)

i = 0
  
# 存储形状名称的列表(未实际使用)
for contour in contours:
    if i == 0:
        i = 1
        continue

    approx = cv2.approxPolyDP(
        contour, 0.01 * cv2.arcLength(contour, True), True)

    cv2.drawContours(img, [contour], 0, (0, 0, 0), 5)
  
    # 计算形状中心点
    M = cv2.moments(contour)
    if M['m00'] != 0.0:
        x = int(M['m10']/M['m00'])
        y = int(M['m01']/M['m00'])
  
cv2.imshow('shapes', img)
  
cv2.waitKey(0)
cv2.destroyAllWindows()

输入与输出效果

输入散点图
检测结果图

问题原因

原代码使用cv2.THRESH_BINARY固定阈值(127)处理,会将灰度值高于127的像素转为白色,低于127的转为黑色。浅色点的灰度值接近白色(高于127),阈值处理后会与背景融合,无法形成可被findContours识别的轮廓。

解决方案

1. 反向二值化+自动阈值

使用cv2.THRESH_BINARY_INV反转二值化效果,让浅色点转为黑色前景;搭配cv2.THRESH_OTSU自动计算最优阈值,无需手动设置固定值,适配不同亮度的图像。

2. 优化轮廓检索模式

改用cv2.RETR_EXTERNAL只检测最外层轮廓,避免获取背景等冗余轮廓,简化后续处理逻辑。

修改后的完整代码

import cv2

img = cv2.imread('808.png')
imgGray = cv2.cvtColor(img, cv2.COLOR_BGR2GRAY)

# 反向二值化+Otsu自动阈值
_, threshold = cv2.threshold(imgGray, 0, 255, cv2.THRESH_BINARY_INV | cv2.THRESH_OTSU)

# 仅检测最外层轮廓
contours, _ = cv2.findContours(threshold, cv2.RETR_EXTERNAL, cv2.CHAIN_APPROX_SIMPLE)

for contour in contours:
    # 过滤过小的噪声轮廓
    if cv2.contourArea(contour) < 10:
        continue
        
    # 绘制点的轮廓
    cv2.drawContours(img, [contour], 0, (0, 0, 0), 5)
    
    # 计算并标记中心点
    M = cv2.moments(contour)
    if M['m00'] != 0.0:
        x = int(M['m10'] / M['m00'])
        y = int(M['m01'] / M['m00'])
        cv2.circle(img, (x, y), 3, (0, 255, 0), -1)

cv2.imshow('all_points_detected', img)
cv2.waitKey(0)
cv2.destroyAllWindows()

额外优化建议

  • 轮廓面积过滤:通过cv2.contourArea过滤面积过小的噪声点,避免误检测。
  • 轮廓点压缩:使用cv2.CHAIN_APPROX_SIMPLE替代cv2.CHAIN_APPROX_NONE,减少轮廓点数量,提升处理效率。

内容的提问来源于stack exchange,提问作者KG_1

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.08.19 18:40:29