使用Opencv对图片处理的各种原理-从图片的储存形式到各种处理过程(必看)(上)

    技术2023-12-15  73

    简介

    对于主攻计算机视觉的我们来说,对图片处理几乎时时刻刻都在进行。但在复现了几个网络后,我开始对整个网络过程中,图片到底是怎么变换的产生好奇。因此,在实验室中借阅了本相关的书籍(《Opencv算法精解-基于Python与C++》),通过一段时间的学习,整理。总算大致了解了图片在计算机上的各种转换过程。尤其在学习完之后,原来如此之情油然而生。因此,在这里,希望研究本方向的其他同学(特指入门者,资深学者请忽略)能先了解图片的原理之后,再开始入门深度学习。为方便大家,我在此做了一些总结,可以省去大部分时间,以及有些书籍中的opencv版本过低,某些算法已经改变。希望本篇博客能给大家带来帮助,也欢迎大家指出问题。

    目录

    Opencv简介图像数值化几何变化对比度增强图像平滑阈值分割形态学处理

    Opencv简介

    OpenCV是一个基于BSD许可(开源)发行的跨平台计算机视觉库,可以运行在Linux、Windows、Android和Mac OS操作系统上。它轻量级而且高效——由一系列 C 函数和少量 C++ 类构成,同时提供了Python、Ruby、MATLAB等语言的接口,实现了图像处理和计算机视觉方面的很多通用算法。 OpenCV用C++语言编写,它的主要接口也是C++语言,但是依然保留了大量的C语言接口。该库也有大量的Python、Java and MATLAB/OCTAVE(版本2.5)的接口。这些语言的API接口函数可以通过在线文档获得。如今也提供对于C#、Ch、Ruby,GO的支持。

    Opencv的应用领域

    OpenCV 的应用领域非常广泛,包括图像拼接、图像降噪、产品质检、人机交互、人脸识别、动作识别、动作跟踪、无人驾驶等。

    图像数值化

    (之后的所有图片处理,都将以上图为原图)

    Numpy中的ndarrayOpencv中的Mat灰度图像数字化彩色图像数字化

    1.Numpy中的ndarray

    函数说明

    转化为数组形式:np.array(object,dtype=None,copy='K',subok=False,ndmin=0)创建元素为0的数组:np.zeros(shape,dtype=float)创建shape同x的0数组:np.zeros_like(x)创建元素为1的数组:np.ones(shape,dtype=float)创建shape同x的1数组:np.zeros_like(x)

    2.Opencv中的Mat

    基本构成:行数(高),列数(宽),通道数(高)以及数据类型Mat(int rows,int cols,int type) type的基本类型: CV_8UC(n),CV_8SC(n),CV_16SC(n),CV_16UC(n),CV_32SC(n),CV_32FC(n),CV_64FC(n) 构成说明: 前面的数字代表所占的bit数, U:unsign char S:sign int F:float C(n)则代表了n通道 例如: CV_16SC3 代表着2个字节的sign int,通道数为3的类型(1byte = 8bit) (注意:这里的构造函数,只给出了三个参数,并没有给出通道数的构建,其实这已经包括在type的定义中,这主要涉及到了opencv中的type设定)

    3.灰度图像数字化

    所谓的数字化,其实就是化成同行同列的二维数组,而每个坐标存的就是相关的灰度值(0-255) (为什么是0-255?就像上面所说,一个字节存放8bit,而图的储存都是以uint8类型存放,同时计算机时按照二进制存放数值,也就是2的8次方,也就是256)

    补充:色彩深度与灰阶

    色彩深度灰阶色彩深度(Depth of Color),色彩深度又叫色彩位数。视频画面中红、绿、蓝三个颜色通道中每种颜色为N位,总的色彩位数则为3N,色彩深度也就是视频设备所能辨析的色彩范围。目前有18bit、24bit、30bit、36bit、42bit和48bit位等多种。24位色被称为真彩色,R、G、B各8bit,常说的8bit,色彩总数为1670万,如手机参数,多少万色素就这个概念。通常来说,液晶屏幕上人们肉眼所见的一个点,即一个像素,它是由红、绿、蓝(RGB)三原色组成的。每一个基色,其背后的光源都可以显现出不同的亮度级别。而灰阶代表了由最暗到最亮之间不同亮度的层次级别。把三基色每一个颜色从纯色(如纯红)不断变暗到黑的过程中的变化级别划分成为色彩的灰阶,并用数字表示,就是最常见的色彩存储原理。这中间层级越多,所能够呈现的画面效果也就越细腻。以8bit 为例,我们就称之为256灰阶。

    调用函数: cv2.imread(filename,flag)

    filename:文件名flag:读入方法常用:0相当于灰度读入,1相当于彩色读入

    具体flag类型:

    实例:

    3.彩色图像数字化

    原理同上,不多说,直接展示实例。 实例:

    补充:通道的分离与组合

    图片解析: 从图中可看出,每三个BGR就组成了一张图片的一列。因此,实际上可将图片看成一个长方体(如下图,自画图,可能不咋地)。而分离与结合也是基于这三个通道展开。

    分离(split())

    问题: 为什么得到的是三张不同的灰度图?不是已经分离出RGB通道了,应该是红色图,蓝色图,绿色图。

    解答 当调用 imshow(R)时,是把图像的R,G,B三个通道的值都变为R的值,所以图像的颜色三通道值为(R,R,R)同理 imshow(G)和imshow(B)所显示d图像的颜色通道也依次为(G,G,G)和(B,B,B)。而 当三个通道d值相同时,则为灰度图。(注意:在opencv中是按照bgr,而不是rgb,因此在提取时需要特别注意)。

    合并(merge())

    几何变化

    平移放大,缩小旋转投影,极坐标

    仿射变化

    主要是指平移,缩放,旋转,反转,错切五种 原理解析 我们可以将一张图片看成是由无数个点组成的。因此,要实现以上变化,则可以看成对无数个点的操作。从而完成整张图的变换。

    单点操作 推导(引用矩阵变换) 过程 其中A成为仿射变换矩阵。 参数解析

    a,d代表x,y的放大倍数,当m,n都为0时,代表以远点为中心缩放,否则代表(m,n)为中心缩放。(一般情况下,b,c为0)m,n代表平移距离特别的,可进行符合运算,即先平移,再放大,再平移等(需特别注意矩阵的结合律等)

    旋转

    将B点从θ旋转阿尔法到B’ 首先,由图可得: 之后,通过上式可知: 由此可知,放射变化矩阵A为 特别的,当绕(m,n)旋转时:

    补充:插值算法

    具体几个算法可在此博客中查看 在进行变化之后,会使某些坐标的值损失,因此需要进行插值。具体的算法原理在上面的链接中已经非常详细了。因此,在这里主要手写实现一下:最邻近插值以及双线性插值算法。

    最邻近插值 双线性插值

    应用

    投影

    原理相同,不过实在原来的仿射变换矩阵上添加了第三行z(在空间中进行仿射变换)。 步骤

    通过四个点的投影前投影后的对比,求出变换矩阵利用变换矩阵对全图进行计算

    极坐标变换

    该转化过程可回忆高中的极坐标转换(圆的方程),直角坐标系上的圆转化为极坐标上的直线,从而实现了图像的变换。 这是一个opencv4的例子

    直角坐标系转换成极坐标cv2.cartTopolar(array,angleInDegress(角度或者弧度))极坐标转换成直角坐标系 cv2.polarTocart(同上)线性极坐标(cv2.linearPolar(img,center,maxRadius,flags))对数极坐标(cv2.logPolar(img,cemter,M,flags))

    原图 极坐标 线性极坐标 对数极坐标 至此,上半部分的内容结束了,下半部分则解释一下:对比度增强,图像平滑,阈值分割,形态学处理等剩下部分。

    Processed: 0.064, SQL: 10