二. 图像运算、坐标变化、灰度插值
2.1 图像运算
输入两个图像A(x,y)、B(x,y),输出图像C(x,y)
2.1.1 加法运算
定义:
C(x,y)=A(x,y)+B(x,y)
主要用途:
-
去除叠加性噪声:
如果某一图像被一加性随机噪声污染,那可以通过对多个该情境下的图像求平均值来降噪。
-
生成图像叠加效果。
C(x,y)=12α(x,y)+12β(x,y)其中:(α+β=1)
2.1.2 减法运算
定义:
C(x,y)=A(x,y)+B(x,y)
主要用途:
显示两幅图像之间的变化;检测同一场景下两幅图像之间的变化。如:视频中运动目标检测、图像差异检测。
- 图像差异检测(运动目标检测)。
- 去除不需要的叠加性图案。
2.1.3 乘法运算
定义:
C(x,y)=A(x,y)×B(x,y)
主要用途:
图像的局部显示。
EG:用二值模板图像与原图像做乘法运算。
2.2 坐标变化
主要介绍了图像的平移、缩放、旋转,以及计算机坐标系和常用坐标系之间的变换。
思路:通过变换矩阵,对图像进行变换:
⎡⎢⎣x′y′1⎤⎥⎦=⎡⎢⎣t11t12t13t21t22t23001⎤⎥⎦⎡⎢⎣xy1⎤⎥⎦
那么:
x′=t11x+t12y+t13y′=t21x+t22y+t231=0+0+1
由此,可以衍生出:尺度、旋转、平移等变换。
2.2.1 平移
变换矩阵如下:
⎡⎢⎣10tx01ty001⎤⎥⎦
那么变换后的坐标:
{x′=x+txy′=y+ty
注意:变换后画布扩大的,否则会失去信息。
2.2.2 图像的尺度变换
变换矩阵如下:
⎡⎢⎣tx000ty0001⎤⎥⎦
变换后的坐标:
{x′=txxy′=tyy
注意:由于采样间隔并没有改变,也就是说像素点的大小没有变化,那么所谓缩放其实就是像素点数量的变化,因此我们需要对多出来的像素点的灰度级进行计算,这就涉及到了插值算法,下面会讲。
2.2.3 图像的旋转变化
变换矩阵如下:
⎡⎢⎣cosθ−sinθ0sinθcosθ0001⎤⎥⎦
变换后的坐标如下:
{x′=xcosθ−ysinθy′=xsinθ+ycosθ
公式推导:
如果原坐标x=Pcosα,y=Psinα,假设逆时针旋转α角度,那么变化后的坐标为
x′=Pcos(α+θ)=Pcosαcosθ−Psinαsinθ=xcosθ−ysinθy′=Psin(α+θ)=Psinαcosθ+Pcosαsinθ=xsinθ+ycosθ
注意:
- 图像旋转后,会出现许多空白点(像素),对于这些空白点,必须赋予灰度值,否则图片效果会很差,这里同样用到插值算法。
- 这里的旋转适用的坐标轴是以左下角为矩阵,向右为x,向上为y的坐标轴,与openCV中矩阵坐标轴不一致,因此需要坐标轴变换。此外,还需要考虑旋转后图像的大小是否发生变化。映射的流程在空间坐标映射中体现:
2.2.4 空间坐标映射
根据顺序,存在两种映射方式:
- 前向映射:根据(x,y) 推导出(x′,y′)。
- 缺点:可能多个点映射为一个点,也可能存在一些位置没有点映射过来。
- 后向映射,由坐标值(x′,y′)经过反向变换T−1得到原先对应的坐标(x,y),随后采用插值算法确定g(x′,y′)(即(x′,y′)的灰度值)。
二维图像的旋转映射
现在有图像Image,shape为(height,weight),其中有一点像素为P(m,n),我们将图像逆时针旋转θ度,得到Image',shape为(height',weight'),求新的像素位置。
步骤如下:
-
我们先为坐标系命名:
- M为矩阵坐标系,左上角为坐标原点,向下为x的正方向,向右为y的正方向。M为计算机下图像的坐标系。
- N为常用数学坐标系,左下为坐标原点,向右为x的正方向,向上为y轴的正方向。N下变换矩阵生效。
-
变换坐标系:因为题目中的坐标均为M坐标系下,而我们计算像素旋转都是在N坐标系下,因此需要对像素位置进行变换。转换公式为:
若PM(x,y),则:PN(x′,y′)={x′=yy′=height−x−1
因此PN=PN(n,height−m−1),记作PN(x,y)
-
中心旋转:接下来就是选择相对于哪一点进行旋转,因为旋转前后图像的大小会发生变化,因此我们最好不要相对于边角进行旋转,一般选择中心进行旋转,中心坐标为O(weight−12,height−12),记作O(ox,oy)。旋转的步骤如下:
-
因为旋转公式是相对于原点的,因此将图片的中心移动到坐标原点,那么PN(x,y)的坐标变换为:
⎡⎢⎣x′y′1⎤⎥⎦=⎡⎢⎣10−ox01−oy001⎤⎥⎦⎡⎢⎣xy1⎤⎥⎦
得到了P′(x′,y′)
-
开始旋转:
⎡⎢⎣x′′y′′1⎤⎥⎦=⎡⎢⎣cosθ−sinθ0sinθcosθ0001⎤⎥⎦⎡⎢⎣x′y′1⎤⎥⎦
得到旋转后的像素位置:P′′N(x′′,y′′)
-
将图像的中心点移动回原来的位置:
⎡⎢⎣x′′′y′′′1⎤⎥⎦=⎡⎢⎣10o′x01o′y001⎤⎥⎦⎡⎢⎣x′′y′′1⎤⎥⎦
注意:因为图像旋转后宽和高发生了变换,因此移动的尺度也发生了变化,现在是相对于旋转后的图像中心进行移动。
得到旋转后的像素点:P′′′N(x′′′,y′′′)
-
将N坐标系变换回M坐标系,变换公式如下:
若PN(x,y),那么:PM(x′,y′)={x′=height′−y−1y′=x
注意:因为变换后宽和高发生了变换,这里使用的是旋转后的宽和高。
得到结果P′M(height′−y′′′−1,x′′′)
- 后向映射:就是将上述步骤反过来,注意旋转前后图像宽和高的变化。
EG1:
现在有图像矩阵如下:
图像大小为(4,5),像素点P(2,1),将图像旋转90°,求旋转后的像素点的坐标。
- 转化为一般直角坐标系:
PN(x,y){x=1y=4−2−1=1PN(x,y)=PN(1,1)
-
相对于中心点旋转:
-
将中心点移动到原点:
⎡⎢⎣x′y′1⎤⎥⎦=⎡⎢⎣10−201−1.5001⎤⎥⎦⎡⎢⎣111⎤⎥⎦=⎡⎢⎣−1−0.51⎤⎥⎦
-
将图像逆时针旋转90°:
⎡⎢⎣x′′y′′1⎤⎥⎦=⎡⎢⎣0−10100001⎤⎥⎦⎡⎢⎣−1−0.51⎤⎥⎦=⎡⎢⎣0.5−11⎤⎥⎦
-
重新将图像移动回去:这里要注意,新的图像维度为(5,4),因此移动的尺度为(1.5, 2):
⎡⎢⎣x′′′y′′′1⎤⎥⎦=⎡⎢⎣101.5012001⎤⎥⎦⎡⎢⎣0.5−11⎤⎥⎦=⎡⎢⎣211⎤⎥⎦
得到P′′′N(2,1)
- 再将常用坐标系变换回矩阵坐标系:注意旋转后矩阵的大小发生了变化:
PM(x,y)={x=height′′′−y−1=3y=x′′′=2
因此变换后的像素位置为(3,2)。
EG2:将上述过程逆向,得到逆向映射:
- 变换为常用坐标:
PN(x,y)=(2,5−1−3)=(2,1)
-
顺时针旋转90°,也就是逆时针旋转270°:
-
中心移动到坐标原点:
⎡⎢⎣x′y′1⎤⎥⎦=⎡⎢⎣10−1.501−2001⎤⎥⎦⎡⎢⎣211⎤⎥⎦=⎡⎢⎣0.5−11⎤⎥⎦
-
逆时针旋转270°
⎡⎢⎣x′′y′′1⎤⎥⎦=⎡⎢⎣010−100001⎤⎥⎦⎡⎢⎣0.5−11⎤⎥⎦=⎡⎢⎣−1−0.51⎤⎥⎦
-
中心移动回去:注意矩阵的大小发生变化
⎡⎢⎣x′′′y′′′1⎤⎥⎦=⎡⎢⎣102011.5001⎤⎥⎦⎡⎢⎣−1−0.51⎤⎥⎦=⎡⎢⎣111⎤⎥⎦
-
再将坐标系由常用直角坐标系变换为矩阵坐标系:
PN(4−1−1,1)=P(2,1)
2.3 像素灰度插值
原因:
图像中的像素只有整数坐标,坐标值(x′,y′)经过反向映射得到的原坐标值(x,y)很可能并不是整数,那么我们如何确定g(x′,y′)这里就需要泳道灰度插值算法。
常用的有三种办法:
-
最邻近插值算法:
-
双线性插值:
-
原理:就是对像素点在x、y的方向上分别进行一次单线性插值。具体如下:
-
先在x维度上进行第一次单线性插值,得到R1 的灰度值R2:
R1=x2−xx2−x1Q21+x−x1x2−x1Q11R2=x2−xx2−x1Q22+x−x1x2−x1Q12
-
再在y维度上进行一次单线性插值,得到P的灰度值:
P=y2−yy2−y1R1+y−y1R2−R1R2
由此可得g(p)
-
EG:
假设P′(x′,y′)经过反向映射得到的原坐标为P(x,y)为(12.8, 15.3),那么周边四个点分别为:N1(12,15),N2(12,16),N3(13,15),N4(13,16)那么:
R1=16−15.316−15N1+15.3−1516−15N2=0.7N1+0.3N2R2=16−15.316−15N3+15.3−1516−15N4=0.7N3+0.3N4g(P)=13−12.813−12R1+12.8−1213−12R2=0.2R1+0.8R2=0.2∗0.7∗N1+0.2∗0.3N2+0.8∗0.7N3+0.8∗0.3N4
简单来说:根据四个点与像素点P的距离,为不同的像素分配不同的灰度,在双线性中成对角形式。
假设像素点四个临近点依次为:左上、右上、左下、右下N1,N2,N3,N4,对应坐标的绝对值差值依次为(Δx1,Δy1),(Δx2,Δy2),(Δx3,Δy3),(Δx4,Δy4),那么:
g(P)=Δx4∗Δy4∗N1+Δx3∗Δy3∗N2+Δx2∗Δy2∗N3+Δx1∗Δy1∗N4
-
三次内插法:略
【推荐】国内首个AI IDE,深度理解中文开发场景,立即下载体验Trae
【推荐】编程新体验,更懂你的AI,立即体验豆包MarsCode编程助手
【推荐】抖音旗下AI助手豆包,你的智能百科全书,全免费不限次数
【推荐】轻量又高性能的 SSH 工具 IShell:AI 加持,快人一步
· 分享一个免费、快速、无限量使用的满血 DeepSeek R1 模型,支持深度思考和联网搜索!
· 基于 Docker 搭建 FRP 内网穿透开源项目(很简单哒)
· ollama系列01:轻松3步本地部署deepseek,普通电脑可用
· 25岁的心里话
· 按钮权限的设计及实现