使用Python估计欧几里得变换

3
我希望能进行类似于图像分析中标准的“图像配准”的功能,使用特征定位。我要找到一个最佳转换方式,将一组2D坐标A转换成另一组B。但是我想增加一个额外的限制条件,即该转换是“刚性/欧几里得变换”,这意味着没有缩放,只有平移和旋转。通常,如果允许缩放,我会这样做:
 from skimage import io, transform
 destination = array([[1.0,2.0],[1.0,4.0],[3.0,3.0],[3.0,7.0]])
 source = array([[1.2,1.7],[1.1,3.8],[3.1,3.4],[2.6,7.0]])
 T = transform.estimate_transform('similarity',source,destination)

我认为estimate_transform在内部只是解决了一个最小二乘问题。 但我想添加不缩放的约束。

skimage或其他软件包中是否有解决此问题的函数? 可能需要使用scipy、CVXOPT或cvxpy编写自己的优化问题。 需要帮助来表述/实现这个优化问题吗?

编辑: 感谢Stefan van der Walt的回答,以下是我的实现。

from matplotlib.pylab import *
from scipy.optimize import *

def obj_fun(pars,x,src):
    theta, tx, ty = pars
    H = array([[cos(theta), -sin(theta), tx],\
         [sin(theta), cos(theta), ty],
         [0,0,1]])
    src1 = c_[src,ones(src.shape[0])]
    return sum( (x - src1.dot(H.T)[:,:2])**2 )

def apply_transform(pars, src):
    theta, tx, ty = pars
    H = array([[cos(theta), -sin(theta), tx],\
         [sin(theta), cos(theta), ty],
         [0,0,1]])
    src1 = c_[src,ones(src.shape[0])]
    return src1.dot(H.T)[:,:2]

res = minimize(obj_fun,[0,0,0],args=(dst,src), method='Nelder-Mead')
2个回答

4

有了这个额外的约束条件,你不再解决一个线性最小二乘问题,所以你需要使用SciPy的最小化函数之一。你的最小化问题的内部部分会设置一个矩阵H:

H = np.array([[np.cos(theta), -np.sin(theta), tx],
              [np.sin(theta), np.cos(theta), ty],
              [0, 0, 1]])

然后,您需要计算距离。
|x_target - H.dot(x_source)|

对于所有数据点求和误差。现在,你有了一个可以发送到最小化函数的成本函数。你可能还想利用RANSAC,它是可用的skimage.measure.ransac,来拒绝异常值。


谢谢你的回答,我已经实施了它并且它起作用了。 - Gioelelm
我省略了一些细节,例如齐次坐标等等,所以能够如此轻松地让它工作,真是太棒了! - Stefan van der Walt

1

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接