【个人笔记】OpenCV4 C++ 图像处理与视频分析 09课
个人资料,仅供学习使用
修改时间——2022年2月14日 10:59:22
学习课程:OpenCV4 图像处理与视频分析实战教程
课程讲师:贾志刚
09 图像直方图+直方图均衡化+直方图比较
opencv知识点:
- 计算直方图数据 - calcHist
- 四舍五入浮点数 - cvRound
- 寻找最小/最大值 - minMaxLoc
- 均衡灰度图像的直方图 - equalizeHist
- 比较直方图 - compareHist
- 比较直方图的方法 - HistCompMethods
本课所解决的问题:
- 什么是图像直方图?
- 如何绘制彩色图像的一维直方图?
- 如何绘制HSV图像的二维直方图?
- 什么是图像直方图均衡化?
- 如何均衡化灰度图像的直方图?
- 如何均衡化彩色图像的直方图?
- 什么是直方图比较?
- 如何比较直方图?
1.图像直方图
直方图部分地方涉及了归一化,没有归一化基础可以阅读 18 图像像素类型转换与归一化,文章中非常详细。
关于图像直方图以及一维直方图的绘制,可以阅读 24 图像直方图,文章中非常详细。
关于二维直方图的绘制,可以阅读 25 二维直方图,文章中非常详细。
2.直方图均衡化
关于图像直方图的均衡化,可以阅读 26 直方图均衡化,文章中非常详细。
3.直方图比较
引用文章:
- 【opencv学习笔记】026之直方图比较 - compareHist函数详解
- opencv之直方图比较图像相似度
直方图比较的应用
当我们计算完两个图像的直方图后,可以对它们进行对比,并通过对比的结果得到一些结论。
比如
图像相似度比较
如果我们有两张图像,并且这两张图像的直方图一样,或者有极高的相似度,那么在一定程度上,我们可以认为这两幅图是一样的,这就是直方图比较的应用之一。分析图像之间关系
两张图像的直方图反映了该图像像素的分布情况,可以利用直方图比较,来分析两张图像的关系。
直方图比较的方法
对输入的两张图像计算得到直方图H1与H2,并归一化到相同的尺度空间
然后可以通过计算H1与H2的之间的距离得到两个直方图的相似程度,进而比较图像本身的相似程度。
计算标准不同,则计算所得的相似程度不同。
我们称这个标准为衡量直方图相似度的对比标准(比较方法),这里设其为d(H1,H2)。
常用的比较方法有四种:
- 相关性比较(Correlation)——
CV_COMP_CORREL
- 卡方比较(Chi-Square)——
CV_COMP_CHISQR
- 十字交叉性(Intersection)——
CV_COMP_INTERSECT
- 巴氏距离(Bhattacharyya distance)——
CV_COMP_BHATTACHARYYA
更多的比较方法可查阅OpenCV4官方文档
四种方法的原理
相关性比较
相关性比较的公式如下:
如果H1 = H2,即两个图的直方图一样,分子等于分母,值为1,所以在不严格的情况下,当值为1时,可以认为两个图是一样的。
但是也有可能会出现两个图不一样,而两个图的直方图是一样的情况。
因为直方图计算的是像素点个数的分布情况,但是不会显示像素点的位置,所以有可能会出现两幅图片不一样,但是相同像素的个数完全一样,那他们的直方图也是一样的。
不过这种情况,不常有。
相关性比较公式来源于统计学中的相关系数,一般用字母 r 表示。
其中,Cov(X,Y)为X与Y的协方差,sigma[X]为X的标准差,sigma[Y]为Y的标准差。r取值范围[-1,1]
相关系数适合数值与数值之间的关联性分析。
如果两个变量的相关性越强,相关系数就会越接近±1,相关性越弱,相关系数越接近0。
也就是说:
- 相关性比较的值越趋近于0,相似度越低
- 相关性比较的值越趋近于1,相似度越高
卡方比较
卡方比较的公式如下:
通过这个公式我们能够发现,卡方比较和相关性比较恰恰相反,
- 卡方比较的值越趋近于1,相似度越低
- 卡方比较的值越趋近于0,相似度越高
值为0时说明H1= H2,这个时候相似度最高。
卡方比较来源于卡方检验,卡方检验就是统计样本的实际观测值与理论推断值之间的偏离程度,
实际观测值与理论推断值之间的偏离程度就决定卡方值的大小,
- 卡方值越大,越不符合
- 卡方值越小,偏差越小,越趋于符合,
- 若两个值完全相等时,卡方值就为0,表明理论值完全符合。
十字交叉性
十字交叉性的公式如下:
这个就比较简单了,对比H1,H2并求出最小值,最后求和。
巴氏距离
巴氏距离的公式如下:
在直方图相似度计算时,巴氏距离获得的效果最好,但计算是最为复杂的。
巴氏距离和相关性比较类似:
- 巴氏距离的值越趋近于0,相似度越低
- 巴氏距离的值越趋近于1,相似度越高
也就是说:巴氏距离的计算结果,其值完全匹配为1,完全不匹配则为0。
直方图比较演示
现在先介绍一下要用到的API
- compareHist
compareHist
compareHist比较两个直方图共3个参数第1个参数 直方图H1第2个参数 直方图H2H1和H2大小要相同,要事先归一化第3个参数 比较方法(查阅官方文档可知)
比较之前, 一定要先对它们进行归一化处理,因为归一化后的比较才有意义。
本课中演示的直方图比较为BGR色彩空间,采取方式为
- 计算图像的直方图,并归一化到[0~1]之间
- 计算图1和图2、图1和图1的相关性和巴氏距离
也可以用cvtColor()把图像从BGR转换到HSV等其他色彩空间,转换后其他地方一一对应即可
#include <opencv2/opencv.hpp>
#include <iostream>using namespace cv;
using namespace std;void hist_compare() {Mat src1 = imread("D:/WorkSpace/Opencv/images/hahaha.jpg");Mat src2 = imread("D:/WorkSpace/Opencv/images/lena.png");imshow("input1", src1);imshow("input2", src2);int histSize[] = { 256, 256, 256 };int channels[] = { 0, 1, 2 };float c1[] = { 0, 255 };float c2[] = { 0, 255 };float c3[] = { 0, 255 };const float* histRanges[] = { c1, c2, c3 };Mat hist1, hist2;calcHist(&src1, 1, channels, Mat(), hist1, 3, histSize, histRanges, true, false);calcHist(&src2, 1, channels, Mat(), hist2, 3, histSize, histRanges, true, false);// 归一化normalize(hist1, hist1, 0, 1.0, NORM_MINMAX, -1, Mat());normalize(hist2, hist2, 0, 1.0, NORM_MINMAX, -1, Mat());// 相关性比较double c12 = compareHist(hist1, hist2, HISTCMP_CORREL);double c11 = compareHist(hist1, hist1, HISTCMP_CORREL);printf("c12 : %.2f, c11 : %.2f\n", c12, c11);// 比较巴氏距离double h12 = compareHist(hist1, hist2, HISTCMP_BHATTACHARYYA);double h11 = compareHist(hist1, hist1, HISTCMP_BHATTACHARYYA);printf("h12 : %.2f, h11 : %.2f\n", h12, h11);
}int main(int argc, char** argv) {//自写的函数hist_compare();waitKey(0);destroyAllWindows();return 0;
}
如图可知
- 图1图2相关性比较:0.00;图1图1相关性比较:1.00
- 图1图2卡方比较:1.00;图1图1卡方比较:0.00
本课所用API查阅
calcHist
#include <opencv2/imgproc.hpp>
#include <opencv2/highgui.hpp>
using namespace cv;
int main( int argc, char** argv )
{Mat src, hsv;if( argc != 2 || !(src=imread(argv[1], 1)).data )return -1;cvtColor(src, hsv, COLOR_BGR2HSV);// 将色调量化为 30 级// 饱和度为 32 级int hbins = 30, sbins = 32;int histSize[] = {hbins, sbins};// 色调从 0 到 179 变化,见 cvtColorfloat hranges[] = { 0, 180 };// 饱和度从 0(黑-灰-白)到// 255(纯光谱颜色)float sranges[] = { 0, 256 };const float* ranges[] = { hranges, sranges };MatND hist;// 我们从第 0 和第 1 通道计算直方图int channels[] = {0, 1};calcHist( &hsv, 1, channels, Mat(), // 不使用掩码hist, 2, histSize, ranges,true, // 直方图是统一的false );double maxVal=0;minMaxLoc(hist, 0, &maxVal, 0, 0);int scale = 10;Mat histImg = Mat::zeros(sbins*scale, hbins*10, CV_8UC3);for( int h = 0; h < hbins; h++ )for( int s = 0; s < sbins; s++ ){float binVal = hist.at<float>(h, s);int intensity = cvRound(binVal*255/maxVal);rectangle( histImg, Point(h*scale, s*scale),Point( (h+1)*scale - 1, (s+1)*scale - 1),Scalar::all(intensity),-1 );}namedWindow( "Source", 1 );imshow( "Source", src );namedWindow( "H-S Histogram", 1 );imshow( "H-S Histogram", histImg );waitKey();
}
cvRound
minMaxLoc
equalizeHist
merge
compareHist
HistCompMethods
【个人笔记】OpenCV4 C++ 图像处理与视频分析 09课相关推荐
- 【个人笔记】OpenCV4 C++ 图像处理与视频分析 12课
个人资料,仅供学习使用 修改时间--2022年2月19日 14:57:51 学习课程:OpenCV4 图像处理与视频分析实战教程 课程讲师:贾志刚 12 图像模糊 opencv知识点: 高斯模糊 - ...
- 【个人笔记】OpenCV4 C++ 图像处理与视频分析 11课
个人资料,仅供学习使用 修改时间--2022年2月19日 13:28:28 学习课程:OpenCV4 图像处理与视频分析实战教程 课程讲师:贾志刚 11 图像卷积+卷积边缘处理 opencv知识点: ...
- 【个人笔记】OpenCV4 C++ 图像处理与视频分析 10课
个人资料,仅供学习使用 修改时间--2022年2月14日 10:59:22 学习课程:OpenCV4 图像处理与视频分析实战教程 课程讲师:贾志刚 10 图像查找表与颜色表 opencv知识点: 查找 ...
- 【个人笔记】OpenCV4 C++ 图像处理与视频分析 08课
个人资料,仅供学习使用 修改时间--2022年2月13日 10:31:08 学习课程:OpenCV4 图像处理与视频分析实战教程 课程讲师:贾志刚 08 图像通道分离合并与混合 opencv知识点: ...
- 【个人笔记】OpenCV4 C++ 图像处理与视频分析 07课
个人资料,仅供学习使用 修改时间--2022年2月13日 09:51:04 学习课程:OpenCV4 图像处理与视频分析实战教程 课程讲师:贾志刚 07 图形绘制与填充+文字绘制+随机绘制+矩形ROI ...
- 【个人笔记】OpenCV4 C++ 图像处理与视频分析 04课
个人资料,仅供学习使用 修改时间--2022年2月10日 09:16:31 学习课程:OpenCV4 图像处理与视频分析实战教程 课程讲师:贾志刚 04 图像算术操作+调整亮度与对比度+伪装透明度 o ...
- 【个人笔记】OpenCV4 C++ 图像处理与视频分析 03课
个人资料,仅供学习使用 修改时间--2022年2月7日 08:10:05 学习课程:OpenCV4 图像处理与视频分析实战教程 课程讲师:贾志刚 03 Mat 概念介绍+对象创建与赋值+像素读写 op ...
- 【个人笔记】OpenCV4 C++ 图像处理与视频分析 01课
个人资料,仅供学习使用 修改时间--2022年2月5日 09:43:04 学习课程:OpenCV4 图像处理与视频分析实战教程 课程讲师:贾志刚 01 OpenCV4 框架介绍+环境搭建+显示图片 o ...
- 15 OpenCV4图像处理与视频分析实战(50.背景分析-)
15 OpenCV4图像处理与视频分析实战(50.背景分析-) 一.50.背景分析- 来自网易云课堂(贾志刚) 一.50.背景分析- 大家我们就从中呢学会了一些东西,我们如果想把一些就是呃,更多的一些 ...
最新文章
- 没有找到合适的方法来重写_玻璃片价格太高?你可能没有找到合适的供应商
- python时间序列画图_简洁的Python时间序列可视化实现
- centos 删除crontab_centos7 定时任务crontab命令详解
- linux 查看强制位,linux强制位与冒险位
- Visual basic 6读写ini文件
- python内置作用域_python中的作用域
- qt显示rgba8888 如何改 frame_Qt开源作品17-IP地址输入控件
- 6还是5?大还是小?看完这些动图,感觉数学白学了
- java设置默认参数_关于java:如何设置默认方法参数值?
- linux中文显示和输入
- Java编程:贪心算法
- 驱动英特尔核显,让黑苹果流畅运行「OpenCore专门篇」
- Android设置屏幕亮度的两种方式
- Linux查看mpp数据库地址,linux下打开.mpp文件(微软project)._操作系统_rainysia的专栏-CSDN博客...
- the info.plist in the package must contain the CFBundleShortVersionString key.
- str.substring(0,str.length() -1)用法
- 用html和css构建简单的静态网页
- Android BootLoader及两种刷机模式fastboot和recovery
- 锁定“嵌入式AI”应用 中科创达启动第二轮成长
- Linux学习总结-Linux磁盘分区与挂载
热门文章
- pySpark | pySpark.Dataframe使用的坑 与 经历
- docker︱在nvidia-docker中使用tensorflow-gpu/jupyter
- 调整VirtualBox虚拟机分辨率的方法
- 由SELECT ... FROM ... FOR UPDATE想到的
- 《数字图像处理与机器视觉——Visual C++与Matlab实现》——0.2 数字图像处理与识别...
- C++三大特性之多态
- Linux命令行(console)屏幕分辨率调整
- mfc--使用ShellExecute打开另一个可执行程序
- 使用UTL_SMTP包发送邮件
- 30岁的我们还能做什么?