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

OpenCV自适应阈值处理后如何精准提取图像目标点坐标

问题背景

开发需求为定位图像中若干目标点的坐标位置,现有阈值方案存在明显缺陷:

  • 固定阈值法:无法适配目标与背景对比度动态变化的场景,无法覆盖所有使用场景
  • Otsu全局阈值法:部分场景计算得到的阈值偏低,会引入严重噪声干扰

测试发现adaptiveThreshold自适应阈值二值化效果稳定,但后续调用findContours接口检测轮廓时,单个目标点会被识别出多个冗余轮廓,需要可直接标记二值图像连通区域的算法解决该问题。

原有实现代码如下:

vector<Point2f> pointsImage;

Mat gray;
cvtColor(image, gray, COLOR_BGR2GRAY);

Mat blur;
GaussianBlur(gray, blur, cv::Size(5, 5), 0);

Mat bw;
cv::adaptiveThreshold(blur, bw, 255, cv::AdaptiveThresholdTypes::ADAPTIVE_THRESH_MEAN_C, THRESH_BINARY_INV, 7, 5);

vector<vector<Point>> contours;
vector<Vec4i> hierarchy;
findContours(bw, contours, hierarchy, RETR_TREE, CHAIN_APPROX_SIMPLE);
for (size_t i = 0; i < contours.size(); i++ ) {

    if (isContourConvex(contours[i])) {

        Moments M = moments(contours[i]);
        Point2f c(M.m10/M.m00, M.m01/M.m00);

        if (!isnan(c.x) && !isnan(c.y) && !isinf(c.x) && !isinf(c.y)) pointsImage.push_back(c);

    }

}
解决方案

OpenCV原生提供二值图连通区域标记接口connectedComponentsWithStats,可直接替代findContours方案,从根源避免单目标多轮廓的问题。

问题原因

单个目标点被识别出多个冗余轮廓,是因为自适应阈值输出的二值图中,目标区域边缘可能存在细碎缺口、内部可能存在微小空洞,findContours在RETR_TREE模式下会将外轮廓、内部空洞轮廓全部识别输出,最终产生冗余结果。

实现代码

vector<Point2f> pointsImage;

Mat gray;
cvtColor(image, gray, COLOR_BGR2GRAY);

Mat blur;
GaussianBlur(gray, blur, cv::Size(5, 5), 0);

Mat bw;
cv::adaptiveThreshold(blur, bw, 255, cv::ADAPTIVE_THRESH_MEAN_C, THRESH_BINARY_INV, 7, 5);

// 可选:形态学闭运算填补目标区域微小缺口、空洞,避免单个目标被拆分为多个连通域
Mat kernel = getStructuringElement(MORPH_RECT, cv::Size(3,3));
morphologyEx(bw, bw, MORPH_CLOSE, kernel);

Mat labels, stats, centroids;
// 8邻域连通域标记,输出标签图、连通域统计信息、连通域质心
int connectedCount = connectedComponentsWithStats(bw, labels, stats, centroids, 8, CV_32S);

// 跳过标签为0的背景区域,遍历所有前景连通域
for (int i = 1; i < connectedCount; i++) {
    // 按连通域面积过滤噪声,面积阈值根据实际目标点大小调整
    int area = stats.at<int>(i, CC_STAT_AREA);
    if (area < 2 || area > 100) {
        continue;
    }
    // 直接读取连通域质心坐标,无需额外计算轮廓矩
    Point2f c(centroids.at<double>(i, 0), centroids.at<double>(i, 1));
    pointsImage.push_back(c);
}

方案优势

  • 连通域标记会将邻域内相连的像素划分为同一区域,单个目标只要属于同一个连通块就只会输出一个质心,完全解决冗余轮廓问题
  • 接口内置质心计算逻辑,无需手动计算轮廓矩,运行效率高于轮廓检测方案
  • 可直接通过接口返回的连通域面积、宽高属性做噪声过滤,比原有的轮廓凸性判断逻辑鲁棒性更强

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.08.27 04:39:36