kzampog / cilantro

A lean C++ library for working with point cloud data
MIT License
1.02k stars 207 forks source link

assignment of the sigma in RBFKernelWeightEvaluator #19

Closed etudemin closed 5 years ago

etudemin commented 5 years ago

Hi,

For the non-rigid icp, I am not pretty sure about two details in calculating the weightings.

First, in class DefaultCombinedMetricSparseWarpFieldICPEntities, control_weight_eval and reg_weighteval are defined as RBFKernelWeightEvaluator, and their corresponding sigmas are assigned by the following code in non_rigid_icp.cpp.

float control_res = 0.025f;
float src_to_control_sigma = 0.5f*control_res;
float regularization_sigma = 3.0f*control_res;

icp.controlWeightEvaluator().setSigma(src_to_control_sigma);
icp.regularizationWeightEvaluator().setSigma(regularization_sigma);

It seems that the sigmas are basically based on the resolution of the control nodes.

Now I am trying to generate the control nodes by myself (ps. not to use the function cilantro::PointsGridDownsampler3f, and the distance between each control node is constant ), but the meanings of control_res and the 0.5f/3.0f in those sigmas are not very clear to me. Would you kindly give me some suggestion?

Second, the evaluators of the data terms (point-to-point and point-to-plane) are both UnityWeightEvaluator. I am considering replacing them with the RBFKernelWeightEvaluator, so the weighting of each correspondence would be different. What do you think? Or are there some considerations of using the UnityWeightEvaluator in data terms?

Thank you very much!

kzampog commented 5 years ago

Hi,

I would suggest to just use whatever empirically works well!

The important thing for the blending sigma (src_to_control_sigma) is that node effects overlap, so that local transformations are smoothly interpolated over the source geometry (e.g., no staircase effect after warping), but at the same time node effects should be local enough so that you don't get an excessively smooth warp field.

Note that, in the example, we use kNN neighborhoods for both the point-to-node mapping and the regularization graph. A very large sigma in this case would have a similar effect to using a UnityWeightEvaluator in the first place.

You could have a look at the "DynamicFusion: Reconstruction and Tracking of Non-rigid Scenes in Real-Time" paper for some other design choices for both weighting schemes. In the paper, they have a radius parameter per control node (which gives the blending RBF sigma) and use the max radius between two neighboring regularization nodes to weight that regularization term.

You can also write custom weight evaluation functors to suit your needs.

About weighting the correspondences, it is perfectly valid to use RBFKernelWeightEvaluator to give 'safer' matches a higher weight. I am not sure how much of a difference that would make in practice, though, as we typically use a small correspondence rejection threshold anyway and assigning smaller weights to farther correspondences might simply cause the process to just converge more slowly.

Hope that helps!

etudemin commented 5 years ago

Hi,

Thank you for your suggestions! It's really helpful. :)