Skip to content

Commit 845f25f

Browse files
committed
Improves Symmetric ICP tests
Adds more comprehensive tests for the Symmetric ICP registration pipeline, covering various scenarios such as empty correspondence sets, missing normals, and convergence behavior. These improvements enhance the reliability and robustness of the algorithm.
1 parent 31faa3b commit 845f25f

File tree

1 file changed

+38
-38
lines changed

1 file changed

+38
-38
lines changed

cpp/tests/pipelines/registration/SymmetricICP.cpp

Lines changed: 38 additions & 38 deletions
Original file line numberDiff line numberDiff line change
@@ -29,17 +29,17 @@ TEST(SymmetricICP, TransformationEstimationSymmetricConstructor) {
2929
TEST(SymmetricICP, TransformationEstimationSymmetricComputeRMSE) {
3030
geometry::PointCloud source;
3131
geometry::PointCloud target;
32-
32+
3333
// Create simple test point clouds with normals
3434
source.points_ = {{0, 0, 0}, {1, 0, 0}, {0, 1, 0}};
3535
source.normals_ = {{0, 0, 1}, {0, 0, 1}, {0, 0, 1}};
36-
36+
3737
target.points_ = {{0.1, 0.1, 0.1}, {1.1, 0.1, 0.1}, {0.1, 1.1, 0.1}};
3838
target.normals_ = {{0, 0, 1}, {0, 0, 1}, {0, 0, 1}};
39-
39+
4040
registration::CorrespondenceSet corres = {{0, 0}, {1, 1}, {2, 2}};
4141
registration::TransformationEstimationSymmetric estimation;
42-
42+
4343
double rmse = estimation.ComputeRMSE(source, target, corres);
4444
EXPECT_GT(rmse, 0.0);
4545
}
@@ -49,43 +49,43 @@ TEST(SymmetricICP, TransformationEstimationSymmetricComputeRMSEEmptyCorres) {
4949
geometry::PointCloud target;
5050
registration::CorrespondenceSet corres;
5151
registration::TransformationEstimationSymmetric estimation;
52-
52+
5353
double rmse = estimation.ComputeRMSE(source, target, corres);
5454
EXPECT_EQ(rmse, 0.0);
5555
}
5656

5757
TEST(SymmetricICP, TransformationEstimationSymmetricComputeRMSENoNormals) {
5858
geometry::PointCloud source;
5959
geometry::PointCloud target;
60-
60+
6161
source.points_ = {{0, 0, 0}, {1, 0, 0}};
6262
target.points_ = {{0.1, 0.1, 0.1}, {1.1, 0.1, 0.1}};
6363
// No normals
64-
64+
6565
registration::CorrespondenceSet corres = {{0, 0}, {1, 1}};
6666
registration::TransformationEstimationSymmetric estimation;
67-
67+
6868
double rmse = estimation.ComputeRMSE(source, target, corres);
6969
EXPECT_EQ(rmse, 0.0);
7070
}
7171

7272
TEST(SymmetricICP, TransformationEstimationSymmetricComputeTransformation) {
7373
geometry::PointCloud source;
7474
geometry::PointCloud target;
75-
75+
7676
// Create test point clouds with normals
7777
source.points_ = {{0, 0, 0}, {1, 0, 0}, {0, 1, 0}, {1, 1, 0}};
7878
source.normals_ = {{0, 0, 1}, {0, 0, 1}, {0, 0, 1}, {0, 0, 1}};
79-
79+
8080
target.points_ = {{0, 0, 0}, {1, 0, 0}, {0, 1, 0}, {1, 1, 0}};
8181
target.normals_ = {{0, 0, 1}, {0, 0, 1}, {0, 0, 1}, {0, 0, 1}};
82-
82+
8383
registration::CorrespondenceSet corres = {{0, 0}, {1, 1}, {2, 2}, {3, 3}};
8484
registration::TransformationEstimationSymmetric estimation;
85-
86-
Eigen::Matrix4d transformation =
85+
86+
Eigen::Matrix4d transformation =
8787
estimation.ComputeTransformation(source, target, corres);
88-
88+
8989
// Should be close to identity for perfect correspondence
9090
EXPECT_TRUE(transformation.isApprox(Eigen::Matrix4d::Identity(), 1e-3));
9191
}
@@ -95,92 +95,92 @@ TEST(SymmetricICP, TransformationEstimationSymmetricComputeTransformationEmptyCo
9595
geometry::PointCloud target;
9696
registration::CorrespondenceSet corres;
9797
registration::TransformationEstimationSymmetric estimation;
98-
99-
Eigen::Matrix4d transformation =
98+
99+
Eigen::Matrix4d transformation =
100100
estimation.ComputeTransformation(source, target, corres);
101-
101+
102102
EXPECT_TRUE(transformation.isApprox(Eigen::Matrix4d::Identity()));
103103
}
104104

105105
TEST(SymmetricICP, TransformationEstimationSymmetricComputeTransformationNoNormals) {
106106
geometry::PointCloud source;
107107
geometry::PointCloud target;
108-
108+
109109
source.points_ = {{0, 0, 0}, {1, 0, 0}};
110110
target.points_ = {{0.1, 0.1, 0.1}, {1.1, 0.1, 0.1}};
111111
// No normals
112-
112+
113113
registration::CorrespondenceSet corres = {{0, 0}, {1, 1}};
114114
registration::TransformationEstimationSymmetric estimation;
115-
116-
Eigen::Matrix4d transformation =
115+
116+
Eigen::Matrix4d transformation =
117117
estimation.ComputeTransformation(source, target, corres);
118-
118+
119119
EXPECT_TRUE(transformation.isApprox(Eigen::Matrix4d::Identity()));
120120
}
121121

122122
TEST(SymmetricICP, RegistrationSymmetricICP) {
123123
geometry::PointCloud source;
124124
geometry::PointCloud target;
125-
125+
126126
// Create test point clouds with normals
127127
source.points_ = {{0, 0, 0}, {1, 0, 0}, {0, 1, 0}};
128128
source.normals_ = {{0, 0, 1}, {0, 0, 1}, {0, 0, 1}};
129-
129+
130130
// Target is slightly translated
131131
target.points_ = {{0.05, 0.05, 0.05}, {1.05, 0.05, 0.05}, {0.05, 1.05, 0.05}};
132132
target.normals_ = {{0, 0, 1}, {0, 0, 1}, {0, 0, 1}};
133-
133+
134134
registration::TransformationEstimationSymmetric estimation;
135135
registration::ICPConvergenceCriteria criteria;
136-
137-
registration::RegistrationResult result =
136+
137+
registration::RegistrationResult result =
138138
registration::RegistrationSymmetricICP(
139139
source, target, 0.1, Eigen::Matrix4d::Identity(), estimation, criteria);
140-
140+
141141
EXPECT_GT(result.correspondence_set_.size(), 0);
142142
EXPECT_GT(result.fitness_, 0.0);
143143
EXPECT_GE(result.inlier_rmse_, 0.0);
144144
}
145145

146146
TEST(SymmetricICP, RegistrationSymmetricICPConvergence) {
147147
utility::random::Seed(42);
148-
148+
149149
// Create a more complex test case
150150
geometry::PointCloud source;
151151
geometry::PointCloud target;
152-
152+
153153
// Generate random points with normals
154154
const int num_points = 50;
155155
utility::random::UniformRealGenerator<double> rand_gen(0.0, 10.0);
156156
for (int i = 0; i < num_points; ++i) {
157157
double x = rand_gen();
158158
double y = rand_gen();
159159
double z = rand_gen();
160-
160+
161161
source.points_.push_back({x, y, z});
162162
source.normals_.push_back({0, 0, 1}); // Simple normal for testing
163163
}
164-
164+
165165
// Create target by transforming source with known transformation
166166
Eigen::Matrix4d true_transformation = Eigen::Matrix4d::Identity();
167167
true_transformation(0, 3) = 0.1; // Small translation in x
168168
true_transformation(1, 3) = 0.05; // Small translation in y
169-
169+
170170
target = source;
171171
target.Transform(true_transformation);
172-
172+
173173
registration::TransformationEstimationSymmetric estimation;
174174
registration::ICPConvergenceCriteria criteria(1e-6, 1e-6, 30);
175-
176-
registration::RegistrationResult result =
175+
176+
registration::RegistrationResult result =
177177
registration::RegistrationSymmetricICP(
178178
source, target, 0.5, Eigen::Matrix4d::Identity(), estimation, criteria);
179-
179+
180180
// Check that registration converged to reasonable result
181181
EXPECT_GT(result.fitness_, 0.5);
182182
EXPECT_LT(result.inlier_rmse_, 1.0);
183183
}
184184

185185
} // namespace tests
186-
} // namespace open3d
186+
} // namespace open3d

0 commit comments

Comments
 (0)