OpenCv之图像二值化

目录

一、图像二值化的核心本质

[二、OpenCV 中二值化的核心方法](#二、OpenCV 中二值化的核心方法)

[2.1 固定阈值二值化(cv::threshold)](#2.1 固定阈值二值化(cv::threshold))

[2.2 自动最优固定阈值(Otsu / 三角法)](#2.2 自动最优固定阈值(Otsu / 三角法))

[2.3 自适应阈值二值化(cv::adaptiveThreshold)](#2.3 自适应阈值二值化(cv::adaptiveThreshold))

[三、 二值化测试代码和效果](#三、 二值化测试代码和效果)

[3.1 lean图测试三个算法](#3.1 lean图测试三个算法)

[3.2 以扫描文档处理为例](#3.2 以扫描文档处理为例)


一、图像二值化的核心本质

图像二值化是将灰度图像 (0~255)转换为纯黑白图像(仅 0 和 255 两个值)的过程,核心是通过「阈值」区分前景(目标)和背景:

  • 像素值 > 阈值 → 设为 255(白)
  • 像素值 ≤ 阈值 → 设为 0(黑)(或反向)

二值化是图像分割、轮廓检测、字符识别、缺陷检测 的基础,能大幅简化图像数据,突出目标区域。

二、OpenCV 中二值化的核心方法

OpenCV 提供两类二值化方法:固定阈值二值化 (手动设阈值)和自适应阈值二值化(自动算阈值),还有拓展的 Otsu / 三角法(自动找最优固定阈值)。

2.1 固定阈值二值化(cv::threshold)

cpp 复制代码
double threshold(
    InputArray src,       // 输入:单通道灰度图(必须!)
    OutputArray dst,      // 输出:二值化图像
    double thresh,        // 手动设定的阈值(0~255)
    double maxval,        // 超过阈值的像素赋值(通常255)
    int type              // 二值化类型
);

二值类型:

2.2 自动最优固定阈值(Otsu / 三角法)

核心原理: 无需手动设阈值,算法自动计算最优阈值 (最大化前景 / 背景分离度),只需在 type 后加 THRESH_OTSUTHRESH_TRIANGLE

  • THRESH_OTSU:适用于双峰直方图(前景和背景像素值分布明显分开);
  • THRESH_TRIANGLE:适用于单峰直方图(如医学图像、暗背景亮目标)。

2.3 自适应阈值二值化(cv::adaptiveThreshold)

核心原理: 针对光照不均 的图像(如阴影、渐变背景),为每个像素计算局部阈值 (以该像素为中心的邻域均值 / 高斯加权均值),能避免固定阈值的 "局部过曝 / 过暗" 问题。函数原型:

复制代码
void adaptiveThreshold(
    InputArray src,       // 输入:单通道灰度图
    OutputArray dst,      // 输出:二值化图像
    double maxValue,      // 最大值(通常255)
    int adaptiveMethod,   // 局部阈值计算方式
    int thresholdType,    // THRESH_BINARY/THRESH_BINARY_INV
    int blockSize,        // 邻域大小(奇数,如3、5、7、11)
    double C              // 常数:阈值 = 邻域均值 - C(调对比度)
);

关键参数

  • adaptiveMethod
    • ADAPTIVE_THRESH_MEAN_C:邻域算术均值作为阈值(速度快);
    • ADAPTIVE_THRESH_GAUSSIAN_C:邻域高斯加权均值作为阈值(效果更平滑);
  • blockSize:邻域越大,二值化越 "模糊";越小,越保留细节(需试 3/5/7/11);
  • C:减去的常数(正数→降低阈值,更多像素变白;负数→提高阈值,更多像素变黑)。

三、 二值化测试代码和效果

3.1 lean图测试三个算法

固定阈值 自动最优固定阈值和自适应阈值方法的二值化。

cpp 复制代码
void testBinaryImage()
{
	Mat GrayMat = imread(R"(D:\Study\OpenCvStudy\lean.jpg)", ImreadModes::IMREAD_GRAYSCALE);
	Mat Thresh_BinaryMat,Threah_BinaryInvMat,TruncMat,TozeoMat,TozeoInvMat;
	//阈值有效
	threshold(GrayMat, Thresh_BinaryMat, 125, 255, THRESH_BINARY);
	threshold(GrayMat, Threah_BinaryInvMat, 125, 255, THRESH_BINARY_INV);
	threshold(GrayMat, TruncMat, 125, 255, THRESH_TRUNC);
	threshold(GrayMat, TozeoMat, 125, 255, THRESH_TOZERO);
	threshold(GrayMat, TozeoInvMat, 125, 255, THRESH_TOZERO_INV);

	Mat Thresh_OTSU_Mat, Thresh_TRIANGLE_Mat;
	//两个算法自己取最优阈值 只支持灰度图
	threshold(GrayMat, Thresh_OTSU_Mat, 125, 255, THRESH_OTSU);
	threshold(GrayMat, Thresh_TRIANGLE_Mat, 125, 255, THRESH_TRIANGLE);
	//自适应法 均值法和高斯法
	Mat Thresh_Mean_Mat, Thresh_Gauss_Mat;
	adaptiveThreshold(GrayMat, Thresh_Mean_Mat,255, AdaptiveThresholdTypes::ADAPTIVE_THRESH_MEAN_C,THRESH_BINARY,55,0);
	adaptiveThreshold(GrayMat, Thresh_Gauss_Mat, 255, AdaptiveThresholdTypes::ADAPTIVE_THRESH_GAUSSIAN_C, THRESH_BINARY, 55, 0);

	imshow("GrayMat", GrayMat);
	imshow("Thresh_BinaryMat", Thresh_BinaryMat);
	imshow("Threah_BinaryInvMat", Threah_BinaryInvMat);
	imshow("TruncMat", TruncMat);
	imshow("TozeoMat", TozeoMat);
	imshow("TozeoInvMat", TozeoInvMat);
	imshow("Thresh_OTSU_Mat", Thresh_OTSU_Mat);
	imshow("Thresh_TRIANGLE_Mat", Thresh_TRIANGLE_Mat);
	waitKey();
}

3.2 以扫描文档处理为例

cpp 复制代码
int testBinaryImage2() {
	// 读取灰度图(必须单通道!)
	Mat img = imread(R"(D:\Study\OpenCvStudy\Test.jpg)", ImreadModes::IMREAD_GRAYSCALE);
	if (img.empty()) return -1;

	// 固定阈值二值化(白底黑字)
	Mat binary1;
	threshold(img, binary1, 127, 255, THRESH_BINARY); // 阈值127

	// 反向二值化(黑底白字)
	Mat binary2;
	threshold(img, binary2, 127, 255, THRESH_BINARY_INV);


	// Otsu 自动找阈值(thresh设0即可,函数返回最优值)
	Mat Otusbinary;
	double otsu_thresh = threshold(img, Otusbinary, 0, 255, THRESH_BINARY | THRESH_OTSU);
	cout << "Otsu 自动计算的最优阈值:" << otsu_thresh << endl;

	// 自适应阈值
	Mat binary_adaptive;
	adaptiveThreshold(
		img, binary_adaptive, 255,
		ADAPTIVE_THRESH_GAUSSIAN_C, // 高斯加权均值
		THRESH_BINARY_INV,          // 白底黑字
		11,                         // 邻域大小11×11
		2                           // 常数C=2
	);


	// 显示
	imshow("原图", img);
	imshow("THRESH_BINARY(白底黑字)", binary1);
	imshow("THRESH_BINARY_INV(黑底白字)", binary2);
	imshow("THRESH_OTSU(白底黑字)", Otusbinary);
	imshow("adaptiveThreshold(白底黑字)", binary_adaptive);
	waitKey(0);
	return 0;
}
相关推荐
永霖光电_UVLED2 小时前
将硅基 N 极性 GaN HEMT 扩展至 8 英寸晶圆
人工智能
Daydream.V2 小时前
Opencv——图像形态学和边缘检测
人工智能·opencv·计算机视觉
智哪儿2 小时前
小米 “养龙虾”:手机 Agent 落地,智能家居十年困局被撬开
人工智能·ai·智能体
ZTLJQ2 小时前
深入理解One-Class SVM:无监督异常检测的精准利器
人工智能·机器学习·支持向量机
汇智信科2 小时前
透明地质保障系统:以数字孪生赋能矿井安全高效开采
人工智能·信息可视化
咚咚王者2 小时前
人工智能之语言领域 自然语言处理 第二章 语言学基础
人工智能·自然语言处理
云烟成雨TD2 小时前
Spring AI 1.x 系列【9】ChatOptions 配置解析
java·人工智能·spring
茗创科技2 小时前
Molecular Psychiatry|将言语模式与情感性及精神病性障碍中的脑结构联系起来:一种整合性的自然语言处理方法
人工智能·自然语言处理
@大迁世界2 小时前
32.CSS魔术师 (CSS Houdini)
前端·css·人工智能·tensorflow·houdini