图像对比度、亮度、饱和度增强算法浅析与代码实现-基础篇(附源码)

一、背景

图像增强作为视频后处理中画质增强技术的一部分,指的是通过调整图片和视频图像画面的饱和度特性,使得画面色彩更加丰富和逼真,提升人的视觉主观感受。由于设备摄像头的多样性,部分摄像头在视频采集时存在饱和度不足,画面发灰,色彩寡淡等问题,这些情况在拍摄室外景物和颜色丰富的场景时尤其容易出现。这些问题可以通过算法的后处理调整进行改善。色彩增强配合视频降噪,暗光增强,对比度调整,边缘增强等技术,可以对视频画质起到较大的提升作用。

二、基本概念

HSV与RGB概念介绍

HSV(Hue, Saturation, Value)和 RGB(Red, Green, Blue)是两种不同的颜色表示方法,各自有不同的特点和应用场景。

RGB(红、绿、蓝)

RGB 是一种基于光的颜色表示方法,通过红、绿、蓝三个颜色通道的不同组合来表示各种颜色。每个通道的值范围通常是 0 到 255。

特点:
  • 加色模型:RGB 是一种加色模型,主要用于显示器、电视、相机等基于发光原理的设备。
  • 颜色表示直观:直接表示颜色,但不容易进行颜色操作,例如调节亮度、饱和度等。
颜色表示:
  • 纯红色:RGB(255, 0, 0)
  • 纯绿色:RGB(0, 255, 0)
  • 纯蓝色:RGB(0, 0, 255)
  • 白色:RGB(255, 255, 255)
  • 黑色:RGB(0, 0, 0)

三、代码实现-基础篇(OpenCV+C)

通过OpenCV我们可以实现简单的基于RGB图像的亮度、对比度的变换(增强或者减弱),代码如下:

int AdjustImgRGB() {
	// 读取图像
	Mat src = imread("D:\\测试视频\\1.jpg");
	if (src.empty()) {
		cout << "could not load image." << endl;
		return -1;
	}

	// 调整亮度和对比度调整参数

	double alphaB = 1.5; // 对比度调整系数(1.0-3.0)
	double alphaG = 1.5; // 对比度调整系数(1.0-3.0)
	double alphaR = 1.5; // 对比度调整系数(1.0-3.0)
	int beta = 0;      // 亮度偏移量(0-100)

	// 新建目标图像
	Mat dst = Mat::zeros(src.size(), src.type());

	int rows = src.rows;
	int cols = src.cols;
#if 0
	for (int row = 0; row < rows - 1; row++) {
		for (int col = 0; col < cols - 1; col++) {
			// 获取像素
			int b = src.at<Vec3b>(row, col)[0];
			int g = src.at<Vec3b>(row, col)[1];
			int r = src.at<Vec3b>(row, col)[2];

			// 调整亮度和对比度
			dst.at<Vec3b>(row, col)[0] = saturate_cast<uchar>(alphaB * b + beta);
			dst.at<Vec3b>(row, col)[1] = saturate_cast<uchar>(alphaG * g + beta);
			dst.at<Vec3b>(row, col)[2] = saturate_cast<uchar>(alphaR * r + beta);
		}
	}
#else
	src.convertTo(dst, -1, alphaB, beta);
#endif
	Mat res = dst.clone();	//复制原始图片对象,作为储存变换结果的对象

	cv::imwrite("D:\\测试视频\\1-adjust.jpg", res);
	return 0;
}
#endif

通过以上代码我们可以实现对图像亮度和对比度的调整,但是调整的图像会有明显的图像失真(曝光过度或者曝光不足),如下图对比:

原图:
在这里插入图片描述

调整参数 alpha = 1.5,beta=0; 参数值只调整对比度,不调整亮度,调整后图像:

在这里插入图片描述

因为增强了图像对比度导致了图像变的失真,这显然不是我们想要的结果,所以,我们需要对调整后的图像进行校正,我们称之为 gamma(γ)校正,具体实现代码如下:

//γ校正
double gamma_{ 1.2 };	//确定gamma值
Mat lookUpTable(1, 256, CV_8U);	//新建查询表
uchar* p = lookUpTable.ptr();	//获取查询表的指针,方便后面填充值
for (int i{ 0 }; i < 256; ++i)	//填充查询表
	p[i] = saturate_cast<uchar>(pow(i / 255.0, gamma_) * 255.0);	//非线性转换算法

LUT(dst, lookUpTable, res);	//按查询表中的值,替换原始图片中的值

如上代码所示,我们设置一个gamma值,该值为1则为不矫正,0-1则是减弱图像调整效果,大于1则增强调整效果,在上文图像调整代码不变的基础上,我们进行1.5倍的gamma矫正,具体效果如下:
在这里插入图片描述

对比未校正调整参数 alpha = 1.5,beta=0; 调整的图像:

在这里插入图片描述

我们发现亮度有所降低,失真率有所降低,而如果我们调低矫正参数,可以得到意想不到的效果,设置gamma=0.4调整后图像如下:

在这里插入图片描述

我们从上面调整后的图片可以看到,调整后的图像其阴影的地方变的明亮了也变得更清晰了,变相的实现了图像的黑暗变明亮的增强效果,所以我们一般就可以用他来实现图像的亮度增强,感兴趣的同学可以学习以下文章学习更多OpenCV图像处理相关的东西:https://www.w3cschool.cn/opencv/opencv-c6yv2cb1.html

当然,以上代码实现算法依然有其致命的缺陷,我们可以看到图像不管是增强和减弱亮度,图像还是会有不同层度的失真,而且亮度非常难以控制,所以,我们在下一篇文章中会进行进阶篇的讲解,如何在尽量不失真的情况下,增加图像的色彩饱和度和明度。

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值