小型二维点集的简单配准算法
Posted
技术标签:
【中文标题】小型二维点集的简单配准算法【英文标题】:Simple registration algorithm for small sets of 2D points 【发布时间】:2016-04-08 15:24:45 【问题描述】:我正在尝试找到一种简单的算法来找到两组 2D 点(配准)之间的对应关系。一组包含我要查找的对象的模板,第二组主要包含属于感兴趣对象的点,但它可能很嘈杂(缺失点以及不属于对象的附加点) .两组都包含大约 40 个二维点。第二组是第一组的单应性(平移、旋转和透视变换)。
我有兴趣找到一种用于注册的算法以获得点对应。我将使用这些信息来查找两组之间的转换(所有这些都在 OpenCV 中)。
任何人都可以提出可以完成这项工作的算法、库或一小段代码吗?由于我正在处理小型集合,因此不必进行超级优化。目前,我的方法是类似 RANSAC 的算法:
-
从第 1 组和第 2 组中选择 4 个随机点。
计算变换矩阵 H(使用 openCV getPerspective())
使用 H 扭曲第一组点并测试它们如何与第二组点对齐
重复 1-3 N 次并根据某些度量(例如平方和)选择最佳变换。
有什么想法吗?感谢您的意见。
【问题讨论】:
【参考方案1】:您可以只使用cv::findHomography
。这是一种围绕cv::getPerspectiveTransform
的基于RANSAC 的方法。
auto H = cv::findHomography(srcPoints, dstPoints, CV_RANSAC,3);
其中 3 是重投影阈值。
【讨论】:
cv::findHomography
要求两个点集(此处为 srcPoints 和 dstPoints)对应。我有兴趣找出如何找到这种对应关系,即源点云中的哪些点对应于目标点云中的哪些点。 RANSAC 方法仍然需要合理数量的内点。简单地通过两个不协调的点云是行不通的。
我以为你已经有了火柴但想扭曲它们。但是,您只需要一个注册算法。我会尝试稍后回来
@HumamHelfawi 您建议使用哪种注册算法? (在我的例子中,我有一个旋转和平移的、有些嘈杂的集合,我希望与预定义的集合匹配。)【参考方案2】:
解决问题的一种传统方法是在您没有匹配的配对信息时使用点集注册方法。点集注册和你说的方法类似,可以找到matlab实现here。
谢谢
【讨论】:
这确实是一种可能。谢谢。【参考方案3】:你可以使用 python 使用 Open3D 库,它很容易在 Anaconda 中安装。根据您的目的,ICP 应该可以正常工作,因此我们将使用经典的 ICP,它可以最大限度地减少每次迭代中最近点之间的点对点距离。这是注册 2 个云的代码:
import numpy as np
import open3d as o3d
# Parameters:
initial_T = np.identity(4) # Initial transformation for ICP
distance = 0.1 # The threshold distance used for searching correspondences
(closest points between clouds). I'm setting it to 10 cm.
# Read your point clouds:
source = o3d.io.read_point_cloud("point_cloud_1.xyz")
target = o3d.io.read_point_cloud("point_cloud_0.xyz")
# Define the type of registration:
type = o3d.pipelines.registration.TransformationEstimationPointToPoint(False)
# "False" means rigid transformation, scale = 1
# Define the number of iterations (I'll use 100):
iterations = o3d.pipelines.registration.ICPConvergenceCriteria(max_iteration = 100)
# Do the registration:
result = o3d.pipelines.registration.registration_icp(source, target, distance, initial_T, type, iterations)
result 是一个包含 4 个东西的类:转换 T(4x4)、2 个度量(rmse 和适应度)和对应集。
要访问转换:
我经常将它用于从地面激光扫描仪 (TLS) 和机器人 (Velodiny LIDAR) 获得的 3D 云。
使用 MATLAB: 我们将再次使用点对点 ICP,因为您的数据是二维的。这是一个在三角形内随机生成两个点云的最小示例:
% Triangle vértices:
V1 = [-20, 0; -10, 10; 0, 0];
V2 = [-10, 0; 0, 10; 10, 0];
% Create clouds and show pair:
points = 5000
N1 = criar_nuvem_triangulo(V1,points);
N2 = criar_nuvem_triangulo(V2,points);
pcshowpair(N1,N2)
% Registrate pair N1->N2 and show:
[T,N1_tranformed,RMSE]=pcregistericp(N1,N2,'Metric','pointToPoint','MaxIterations',100);
pcshowpair(N1_tranformed,N2)
“criar_nuvem_triangulo”是生成三角形内随机点云的函数:
function [cloud] = criar_nuvem_triangulo(V,N)
% Function wich creates 2D point clouds in triangle format using random
% points
% Parameters: V = Triangle vertices (3x2 Matrix)| N = Number of points
t = sqrt(rand(N, 1));
s = rand(N, 1);
P = (1 - t) * V(1, :) + bsxfun(@times, ((1 - s) * V(2, :) + s * V(3, :)), t);
points = [P,zeros(N,1)];
cloud = pointCloud(points)
end
结果:
【讨论】:
以上是关于小型二维点集的简单配准算法的主要内容,如果未能解决你的问题,请参考以下文章