在matlab中我们可以通过interp2在矩形网格内进行曲线插值,那么在python中有没有有类似的函数呢?有,并且有很多,都在scipy.interpolate模块中。这篇博客主要说两个比较相似的:interp2d和rectBivariateSpline。两者比较相似,如果输入是规整的网格点,那么使用rectBivariateSpline会更快。下面给一些介绍和例子:
官方文档:interp2d rectBivariateSpline
有上面的文档相信已经够了,这里强调用法中几点注意事项:
- 输入虽然标识为x,y,但事实上第一个参数是axis=0,第二个参数对应axis=1
- rectBivariateSpline中控制插值函数阶次的参数是kx,ky
- interp2d中控制插值方法的参数是kind ,kind=’cubic’ 表示三次插值
- 这两个函数,输入参数x,y均为x和y方向上的网格向量
- 在调用插值时,如果需要采样的点构成一个正立的矩形网格的话,那么输入x和y就输入向量就可以,它会输出 x*y 坐标空间上的2d插值结果。如果需要插值的是一系列离散的点,或者不构成正立网格,那么输入的x和y就是一系列点的坐标,它会输出(x,y)坐标空间上离散点的插值结果。指示插值点规则的参数是grid,默认是true的。
我们先看一个grid=True的例子,利用插值缩放图像(resample)的例子:
# 需要導入模塊: from scipy import interpolate [as 別名] # 或者: from scipy.interpolate import RectBivariateSpline [as 別名] def resample_2d(array, sample_pts, query_pts): ''' Resamples 2D array to be sampled along queried points. Args: array (numpy.ndarray): 2D array. sample_pts (tuple): pair of numpy.ndarray objects that contain the x and y sample locations, each array should be 1D. query_pts (tuple): points to interpolate onto, also 1D for each array. Returns: numpy.ndarray. array resampled onto query_pts via bivariate spline. ''' xq, yq = np.meshgrid(*query_pts) interpf = interpolate.RectBivariateSpline(*sample_pts, array) return interpf.ev(yq, xq)
我们再看一个grid=False的例子,利用插值旋转图像(rotation)的例子:
# 需要導入模塊: from scipy import interpolate [as 別名] # 或者: from scipy.interpolate import RectBivariateSpline [as 別名] def rotate_ground(original, theta, horizon=60, half_height=360 / 2, focal=1.0): height, width, channel = original.shape # the target grids yp = range(height - horizon, height) xp = range(0, width) # from pixel to coordinates y0 = (np.array(yp) - half_height) * 1.0 / half_height x0 = (np.array(xp) - width / 2) / (width / 2.0) # form the mesh mesh = MyDataset.generate_meshlist(x0, y0) # compute the source coordinates st = math.sin(theta) ct = math.cos(theta) deno = ct * focal + st * mesh[:, 0] out = np.array([(-st * focal + ct * mesh[:, 0]) / deno, mesh[:, 1] / deno]) # interpolate vout = [] for i in range(3): f = interpolate.RectBivariateSpline(y0, x0, original[- horizon:, :, i]) values = f(out[1, :], out[0, :], grid=False) vout.append(values) lower = np.reshape(vout, (3, width, horizon)).transpose((2, 1, 0)).astype("uint8") # compute the upper part out = np.reshape(out[0, :], (width, horizon)) out = out[:, 0] f = interpolate.interp1d(x0, original[:-horizon, :, :], axis=1, fill_value=(original[:-horizon, 0, :], original[:-horizon, -1, :]), bounds_error=False) ans = f(out) ans = ans.astype("uint8") return np.concatenate((ans, lower), axis=0)
谢谢,希望能有帮助!