2021SC@SDUSC
#open3D KDTree类
本篇对KDTreeFlann类和KDTreeSearchParam类进行源码分析。
KDTreeFlann
KDTreeFlann类:使用FLANN进行最近邻居搜索的KDTree。
注意点:
- 由于需要解析的代码较多,为使代码解读更加清晰,我将代码分析的详细过程写在代码段的注释中。
- 中文部分是源码解读,包含代码分析和遇到的问题。
#pragma once
#include <Eigen/Core>
#include <memory>
#include <vector>
#include "open3d/geometry/Geometry.h"
#include "open3d/geometry/KDTreeSearchParam.h"
#include "open3d/pipelines/registration/Feature.h"
/// @cond
namespace nanoflann {
struct metric_L2;
template <class MatrixType, int DIM, class Distance, bool row_major>
struct KDTreeEigenMatrixAdaptor;
} // namespace nanoflann
/// @endcond
namespace open3d {
namespace geometry {
/// \class KDTreeFlann
/// 使用FLANN进行最近邻居搜索的KDTree。
class KDTreeFlann {
public:
///默认构造函数。
KDTreeFlann();
///参数化构造函数。
///参数data 为KDTree构造所提供的一组数据点。
KDTreeFlann(const Eigen::MatrixXd &data);
///参数化构造函数。
///参数geometry 为构造KDTree所提供的几何图形。
KDTreeFlann(const Geometry &geometry);
///参数化构造函数。
///参数feature 提供一组构造KDTree的特性。
KDTreeFlann(const pipelines::registration::Feature &feature);
~KDTreeFlann();
KDTreeFlann(const KDTreeFlann &) = delete;
KDTreeFlann &operator=(const KDTreeFlann &) = delete;
public:
///通过一个矩阵设置KDTree的数据。
///参数data 构造KDTree的数据点。
bool SetMatrixData(const Eigen::MatrixXd &data);
///设置KDTree的数据。
///
///参数geometry KDTree的几何结构。
bool SetGeometry(const Geometry &geometry);
///根据特性数据设置KDTree的数据。
///参数feature KDTree构造的功能集。
bool SetFeature(const pipelines::registration::Feature &feature);
template <typename T>
int Search(const T &query,
const KDTreeSearchParam ¶m,
std::vector<int> &indices,
std::vector<double> &distance2) const;
template <typename T>
int SearchKNN(const T &query,
int knn,
std::vector<int> &indices,
std::vector<double> &distance2) const;
template <typename T>
int SearchRadius(const T &query,
double radius,
std::vector<int> &indices,
std::vector<double> &distance2) const;
template <typename T>
int SearchHybrid(const T &query,
double radius,
int max_nn,
std::vector<int> &indices,
std::vector<double> &distance2) const;
private:
///通过其他方法提供的数据中设置KDTree数据。
///内部方法,根据特性、几何等方式提供的数据设置KDTree的所有成员。
bool SetRawData(const Eigen::Map<const Eigen::MatrixXd> &data);
protected:
using KDTree_t = nanoflann::KDTreeEigenMatrixAdaptor<
Eigen::Map<const Eigen::MatrixXd>,
-1,
nanoflann::metric_L2,
false>;
std::vector<double> data_;
std::unique_ptr<Eigen::Map<const Eigen::MatrixXd>> data_interface_;
std::unique_ptr<KDTree_t> nanoflann_index_;
size_t dimension_ = 0;
size_t dataset_size_ = 0;
};
} // namespace geometry
} // namespace open3d
KDTreeSearchParam.h
KDTree搜索参数的基类。
#pragma once
namespace open3d {
namespace geometry {
/// \class KDTreeSearchParam
/// KDTree搜索参数的基类。
class KDTreeSearchParam {
public:
/// \enum SearchType
/// 指定搜索的搜索类型。
enum class SearchType {
Knn = 0,
Radius = 1,
Hybrid = 2,
};
public:
virtual ~KDTreeSearchParam() {}
protected:
KDTreeSearchParam(SearchType type) : search_type_(type) {}
public:
///获取搜索参数的搜索类型(KNN, Radius, Hybrid)。
SearchType GetSearchType() const { return search_type_; }
private:
SearchType search_type_;
};
/// \class KDTreeSearchParamKNN
/// KDTree搜索参数为纯KNN搜索。
class KDTreeSearchParamKNN : public KDTreeSearchParam {
public:
///默认构造函数。
///参数knn 指定要搜索的knn类型的邻居。默认是30。
KDTreeSearchParamKNN(int knn = 30)
: KDTreeSearchParam(SearchType::Knn), knn_(knn) {}
public:
///将要搜索的邻居数。
int knn_;
};
/// \class KDTreeSearchParamRadius
/// KDTree搜索参数的纯半径搜索。
class KDTreeSearchParamRadius : public KDTreeSearchParam {
public:
///默认构造函数。
///
///参数radius 指定搜索半径。
KDTreeSearchParamRadius(double radius)
: KDTreeSearchParam(SearchType::Radius), radius_(radius) {}
public:
///搜索半径。
double radius_;
};
/// \class KDTreeSearchParamHybrid
///
///KDTree搜索参数为hybrid KNN和redius搜索。
class KDTreeSearchParamHybrid : public KDTreeSearchParam {
public:
///默认构造函数。
///
///参数radius 指定搜索的半径。
///参数max_nn 最大搜索邻居数。
KDTreeSearchParamHybrid(double radius, int max_nn)
: KDTreeSearchParam(SearchType::Hybrid),
radius_(radius),
max_nn_(max_nn) {}
public:
///搜索半径。
double radius_;
///在最大值时,将搜索max_nn邻居。
int max_nn_;
};
} // namespace geometry
} // namespace open3d
小结
本篇我对KDTree相关的类进行了源码分析,使得我更加了解了open3D对于KDTree的实现方式。下一篇是open3D中OCTree的相关类的源码分析。