51工具盒子

依楼听风雨
笑看云卷云舒,淡观潮起潮落

二维图像双线性插值 python 快速实现

在对二维数据进行 resize / mapping / 坐标转换等操作时,经常会将原本的整数坐标变换为小数坐标,对于非整数的坐标值一种直观有效的插值方式为双线性插值

插值简介 {#插值简介}

双线性插值,又称为双线性内插。在数学上,双线性插值是有两个变量的插值函数的线性插值扩展,其核心思想是在两个方向分别进行一次线性插值。

双线性插值作为数值分析中的一种插值算法,广泛应用在信号处理,数字图像和视频处理等方面。 假设我们出现了需要在四个相邻正方形整数点$(A,B,C,D) $坐标中间(正方形范围内)选择一个点$(a,b)$取近似值的情形。

此时我们已知的是四个点的数值 $V_A,V_B,V_C,V_D$,给定小数坐标 $E(a, b),0 \le a, b \le 1$,如何插值求解E点的数值呢,解决类似问题的方法统称为插值,上图展示公式为双线性插值的计算方法。

最近邻法 (Nearest Interpolation) {#最近邻法-Nearest-Interpolation}

一种最简便的方法为最近邻法,直接取与当前点距离最近的点的值作为插值结果:
$$
V_E=V_{round(a),round(b)}
$$
其中 $round$ 为四舍五入的取整操作,方法简便速度极快,但往往不够精细

双三次插值 (Bicubic interpolation) {#双三次插值-Bicubic-interpolation}

双三次插值是用原图像中16(4*4)个点计算新图像中1个点,效果比较好,但是计算代价过大。

双线性插值 (Bilinear Interpolation) {#双线性插值-Bilinear-Interpolation}

使用一个点进行插值过于粗暴,16个点又过于繁琐,那就使用$E$​点周围4个点的数值来近似求解,这是一种平衡了计算代价和插值效果的折中方案,也是各大变换库的默认插值操作。

双线性插值 {#双线性插值}

通过观察上述动图(可以动手挪一挪)可以清晰地看到,双线性插值本质就是把四个角落的数值按照正方形面积的比例线性加权后的结果。

好吧一句话已经把数学的核心部分讲完了

那么既然理解了本质,数学公式就好写了:
$$
\begin{array}{l}
V_E&=S_{blue}V_A+S_{red}V_B+S_{yellow}V_C+S_{purple}V_D\
&=(X_C-X_E)(Y_C-Y_E)V_A+(X_D-X_E)(Y_E-Y_D)V_B+(X_E-X_A)(Y_E-Y_A)V_C+(X_E-X_B)(Y_B-Y_E)V_D
\end{array}
$$

python 实现 {#python-实现}

在实现时当然 for 循环大法可以解决一切问题,但总归是不太优雅,我们尝试使用 numpy 操作完成双线性插值

假设原始图像 image,变换后的小数坐标 X 矩阵 x_grid,Y 矩阵 y_grid,那么可以使用如下的 bilinear_by_meshgrid 函数快速双线性插值,已经处理好了边界,可以放心使用。

该函数集成在我自己的python库 mtutils 中,可以通过:

直接安装,之后可以直接引用:

参考资料 {#参考资料}



文章链接:
https://www.zywvvd.com/notes/study/image-processing/bilinear-interpolation/bilinear-interpolation/

赞(0)
未经允许不得转载:工具盒子 » 二维图像双线性插值 python 快速实现