网上学习资料一大堆,但如果学到的知识不成体系,遇到问题时只是浅尝辄止,不再深入研究,那么很难做到真正的技术提升。
一个人可以走的很快,但一群人才能走的更远!不论你是正从事IT行业的老鸟或是对IT行业感兴趣的新人,都欢迎加入我们的的圈子(技术交流、学习资源、职场吐槽、大厂内推、面试辅导),让我们一起学习成长!
双线性插值
假设源图像大小为mxn,目标图像为axb。那么两幅图像的边长比分别为:m/a和n/b。注意,通常这个比例不是整数,编程存储的时候要用浮点型。目标图像的第(i,j)个像素点(i行j列)可以通过边长比对应回源图像。其对应坐标为(im/a,jn/b)。显然,这个对应坐标一般来说不是整数,而非整数的坐标是无法在图像这种离散数据上使用的。双线性插值通过寻找距离这个对应坐标最近的四个像素点,来计算该点的值(灰度值或者RGB值)。
若图像为灰度图像,那么(i,j)点的灰度值的数学计算模型是:
f(x,y)=b1+b2x+b3y+b4xy
其中b1,b2,b3,b4是相关的系数。关于其的计算过程如下如下:
如图,已知Q12,Q22,Q11,Q21,但是要插值的点为P点,这就要用双线性插值了,首先在x轴方向上,对R1和R2两个点进行插值,这个很简单,然后根据R1和R2对P点进行插值,这就是所谓的双线性插值。
定义:双线性插值,又称为双线性内插。在数学上,双线性插值是有两个变量的插值函数的线性插值扩展,其核心思想是在两个方向分别进行一次线性插值。
假如我们想得到未知函数
f
f
f在点
P
=
(
x
,
y
)
P=(x, y)
P=(x,y)的值,假设我们已知函数
f
f
f 在
Q
11
=
(
x
1
,
y
1
)
,
Q
12
=
(
x
1
,
y
2
)
,
Q
21
=
(
x
2
,
y
1
)
Q_{11}=\left(x_{1}, y_{1}\right), Q_{12}=\left(x_{1}, y_{2}\right), Q_{21}=\left(x_{2}, y_{1}\right)
Q11=(x1,y1),Q12=(x1,y2),Q21=(x2,y1)及
Q
22
=
(
x
2
,
y
2
)
Q_{22}=\left(x_{2}, y_{2}\right)
Q22=(x2,y2) 四个点的值。
首先在 x 方向进行线性插值,得到
f
(
R
1
)
≈
x
2
−
x
x
2
−
x
1
f
(
Q
11
)
x
−
x
1
x
2
−
x
1
f
(
Q
21
)
Where
R
1
=
(
x
,
y
1
)
f
(
R
2
)
≈
x
2
−
x
x
2
−
x
1
f
(
Q
12
)
x
−
x
1
x
2
−
x
1
f
(
Q
22
)
Where
R
2
=
(
x
,
y
2
)
\begin{aligned} f\left(R_{1}\right) & \approx \frac{x_{2}-x}{x_{2}-x_{1}} f\left(Q_{11}\right)+\frac{x-x_{1}}{x_{2}-x_{1}} f\left(Q_{21}\right) \quad \text { Where } \quad R_{1}=\left(x, y_{1}\right) \ f\left(R_{2}\right) & \approx \frac{x_{2}-x}{x_{2}-x_{1}} f\left(Q_{12}\right)+\frac{x-x_{1}}{x_{2}-x_{1}} f\left(Q_{22}\right) \quad \text { Where } \quad R_{2}=\left(x, y_{2}\right) \end{aligned}
f(R1)f(R2)≈x2−x1x2−xf(Q11)+x2−x1x−x1f(Q21) Where R1=(x,y1)≈x2−x1x2−xf(Q12)+x2−x1x−x1f(Q22) Where R2=(x,y2)
然后在 y 方向进行线性插值,得到
f
(
P
)
≈
y
2
−
y
y
2
−
y
1
f
(
R
1
)
y
−
y
1
y
2
−
y
1
f
(
R
2
)
f§ \approx \frac{y_{2}-y}{y_{2}-y_{1}} f\left(R_{1}\right)+\frac{y-y_{1}}{y_{2}-y_{1}} f\left(R_{2}\right)
f§≈y2−y1y2−yf(R1)+y2−y1y−y1f(R2)
这样就得到所要的结果
f
(
x
,
y
)
f(x, y)
f(x,y),
**f
(
x
,
y
)
≈
f
(
Q
11
)
(
x
2
−
x
1
)
(
y
2
−
y
1
)
(
x
2
−
x
)
(
y
2
−
y
)
f
(
Q
21
)
(
x
2
−
x
1
)
(
y
2
−
y
1
)
(
x
−
x
1
)
(
y
2
−
y
)
f
(
Q
12
)
(
x
2
−
x
1
)
(
y
2
−
y
1
)
(
x
2
−
x
)
(
y
−
y
1
)
f
(
Q
22
)
(
x
2
−
x
1
)
(
y
2
−
y
1
)
(
x
−
x
1
)
(
y
−
y
1
)
\begin{array}{c}{f(x, y) \approx \frac{f\left(Q_{11}\right)}{\left(x_{2}-x_{1}\right)\left(y_{2}-y_{1}\right)}\left(x_{2}-x\right)\left(y_{2}-y\right)+\frac{f\left(Q_{21}\right)}{\left(x_{2}-x_{1}\right)\left(y_{2}-y_{1}\right)}\left(x-x_{1}\right)\left(y_{2}-y\right)} \ {+\frac{f\left(Q_{12}\right)}{\left(x_{2}-x_{1}\right)\left(y_{2}-y_{1}\right)}\left(x_{2}-x\right)\left(y-y_{1}\right)+\frac{f\left(Q_{22}\right)}{\left(x_{2}-x_{1}\right)\left(y_{2}-y_{1}\right)}\left(x-x_{1}\right)\left(y-y_{1}\right)}\end{array}
f(x,y)≈(x2−x1)(y2−y1)f(Q11)(x2−x)(y2−y)+(x2−x1)(y2−y1)f(Q21)(x−x1)(y2−y)+(x2−x1)(y2−y1)f(Q12)(x2−x)(y−y1)+(x2−x1)(y2−y1)f(Q22)(x−x1)(y−y1)**
如果选择一个坐标系统使得
f
f
f 的四个已知点坐标分别为 (0, 0)、(0, 1)、(1, 0) 和 (1, 1),那么插值公式就可以化简为
f
(
x
,
y
)
≈
f
(
0
,
0
)
(
1
−
x
)
(
1
−
y
)
f
(
1
,
0
)
x
(
1
−
y
)
f
(
0
,
1
)
(
1
−
x
)
y
f
(
1
,
1
)
x
y
f(x, y) \approx f(0,0)(1-x)(1-y)+f(1,0) x(1-y)+f(0,1)(1-x) y+f(1,1) x y
f(x,y)≈f(0,0)(1−x)(1−y)+f(1,0)x(1−y)+f(0,1)(1−x)y+f(1,1)xy
或者用矩阵运算表示为:
f
(
x
,
y
)
≈
[
1
−
x
x
]
[
f
(
0
,
0
)
f
(
0
,
1
)
f
(
1
,
0
)
f
(
1
,
1
)
]
[
1
−
y
y
]
f(x, y) \approx\left[\begin{array}{cc}{1-x} & {x}\end{array}\right]\left[\begin{array}{cc}{f(0,0)} & {f(0,1)} \ {f(1,0)} & {f(1,1)}\end{array}\right]\left[\begin{array}{c}{1-y} \ {y}\end{array}\right]
f(x,y)≈[1−xx][f(0,0)f(1,0)f(0,1)f(1,1)][1−yy]
线性插值的结果与插值的顺序无关。首先进行 y 方向的插值,然后进行 x 方向的插值,所得到的结果是一样的。
注意: 源图像和目标图像的原点(0,0)均选择左上角,然后根据插值公式计算目标图像每点像素,假设你需要将一幅5x5的图像缩小成3x3,那么源图像和目标图像各个像素之间的对应关系如下:
只画了一行,用做示意,从图中可以很明显的看到,如果选择右上角为原点(0,0),那么最右边和最下边的像素实际上并没有参与计算,而且目标图像的每个像素点计算出的灰度值也相对于源图像偏左偏上。
那么,让坐标加1或者选择右下角为原点怎么样呢?很不幸,还是一样的效果,不过这次得到的图像将偏右偏下。
最好的方法就是,两个图像的几何中心重合,并且目标图像的每个像素之间都是等间隔的,并且都和两边有一定的边距,这也是matlab和openCV的做法。如下图:
计算对应坐标的时候改为以下公式即可:
int
x
=
(
i
0.5
)
∗
m
/
a
−
0.5
int
y
=
(
j
0.5
)
∗
n
/
b
−
0.5
\begin{array}{l}{\text { int } x=(i+0.5)^{*} \mathrm{m} / \mathrm{a}-0.5} \ {\text { int } y=(j+0.5)^{*} \mathrm{n} / \mathrm{b}-0.5}\end{array}
int x=(i+0.5)∗m/a−0.5 int y=(j+0.5)∗n/b−0.5
代替
int
x
=
i
⋆
m
/
a
int
y
=
j
⋆
n
/
b
\begin{array}{l}{\text { int } \mathrm{x}=\mathrm{i}^{\star} \mathrm{m} / \mathrm{a}} \ {\text { int } \mathrm{y}=\mathrm{j}^{\star} \mathrm{n} / \mathrm{b}}\end{array}
int x=i⋆m/a int y=j⋆n/b
四、双三次(bicubic)插值
双三次插值又称立方卷积插值。三次卷积插值是一种更加复杂的插值方式。该算法利用待采样点周围16个点的灰度值作三次插值,不仅考虑到4 个直接相邻点的灰度影响,而且考虑到各邻点间灰度值变化率的影响。三次运算可以得到更接近高分辨率图像的放大效果,但也导致了运算量的急剧增加。这种算法需要选取插值基函数来拟合数据,其最常用的插值基函数如下所示:
构造BiCubic函数:
W
(
x
)
=
{
(
a
2
)
∣
x
∣
3
−
(
a
3
)
∣
x
∣
2
1
for
∣
x
∣
≤
1
a
∣
x
∣
3
−
5
a
∣
x
∣
2
8
a
∣
x
∣
−
4
a
for
1
<
∣
x
∣
<
2
0
otherwise
W(x)=\left{\begin{array}{ll}{(a+2)|x|{3}-(a+3)|x|{2}+1} & {\text { for }|x| \leq 1} \ {a|x|^{3}-5 a|x|^{2}+8 a|x|-4 a} & {\text { for } 1<|x|<2} \ {0} & {\text { otherwise }}\end{array}\right.
W(x)=⎩⎨⎧(a+2)∣x∣3−(a+3)∣x∣2+1a∣x∣3−5a∣x∣2+8a∣x∣−4a0 for ∣x∣≤1 for 1<∣x∣<2 otherwise
其中,a取-0.5.
BiCubic函数具有如下形状:
网上学习资料一大堆,但如果学到的知识不成体系,遇到问题时只是浅尝辄止,不再深入研究,那么很难做到真正的技术提升。
一个人可以走的很快,但一群人才能走的更远!不论你是正从事IT行业的老鸟或是对IT行业感兴趣的新人,都欢迎加入我们的的圈子(技术交流、学习资源、职场吐槽、大厂内推、面试辅导),让我们一起学习成长!
=
i
⋆
m
/
a
int
y
=
j
⋆
n
/
b
\begin{array}{l}{\text { int } \mathrm{x}=\mathrm{i}^{\star} \mathrm{m} / \mathrm{a}} \ {\text { int } \mathrm{y}=\mathrm{j}^{\star} \mathrm{n} / \mathrm{b}}\end{array}
int x=i⋆m/a int y=j⋆n/b
四、双三次(bicubic)插值
双三次插值又称立方卷积插值。三次卷积插值是一种更加复杂的插值方式。该算法利用待采样点周围16个点的灰度值作三次插值,不仅考虑到4 个直接相邻点的灰度影响,而且考虑到各邻点间灰度值变化率的影响。三次运算可以得到更接近高分辨率图像的放大效果,但也导致了运算量的急剧增加。这种算法需要选取插值基函数来拟合数据,其最常用的插值基函数如下所示:
构造BiCubic函数:
W
(
x
)
=
{
(
a
2
)
∣
x
∣
3
−
(
a
3
)
∣
x
∣
2
1
for
∣
x
∣
≤
1
a
∣
x
∣
3
−
5
a
∣
x
∣
2
8
a
∣
x
∣
−
4
a
for
1
<
∣
x
∣
<
2
0
otherwise
W(x)=\left{\begin{array}{ll}{(a+2)|x|{3}-(a+3)|x|{2}+1} & {\text { for }|x| \leq 1} \ {a|x|^{3}-5 a|x|^{2}+8 a|x|-4 a} & {\text { for } 1<|x|<2} \ {0} & {\text { otherwise }}\end{array}\right.
W(x)=⎩⎨⎧(a+2)∣x∣3−(a+3)∣x∣2+1a∣x∣3−5a∣x∣2+8a∣x∣−4a0 for ∣x∣≤1 for 1<∣x∣<2 otherwise
其中,a取-0.5.
BiCubic函数具有如下形状:
[外链图片转存中…(img-b2PF7fNY-1715538240093)]
[外链图片转存中…(img-X3QgXcFz-1715538240093)]
网上学习资料一大堆,但如果学到的知识不成体系,遇到问题时只是浅尝辄止,不再深入研究,那么很难做到真正的技术提升。
一个人可以走的很快,但一群人才能走的更远!不论你是正从事IT行业的老鸟或是对IT行业感兴趣的新人,都欢迎加入我们的的圈子(技术交流、学习资源、职场吐槽、大厂内推、面试辅导),让我们一起学习成长!