2

我发现使用 Eigen 对象作为参数的函数设计很麻烦。虽然Eigen 文档中的信息很有帮助,但它为模板参数提出了一种尴尬的方法。假设,我们要编写一个几何例程,例如线-平面-交点。一个简单而透明的方法是:

template<typename _Tp> 
bool planeLineIntersect(const Eigen::Matrix<_Tp, 3, 1>& planePoint, 
                        const Eigen::Matrix<_Tp, 3, 1>& planeNormal, 
                        const Eigen::Matrix<_Tp, 3, 1>& linePoint, 
                        const Eigen::Matrix<_Tp, 3, 1>& lineDir,
                        Eigen::Matrix<_Tp, 3, 1>& intersectionPoint)

这看起来相对令人愉悦,并且看到它的人可以了解到每个参数都应该是相同类型的 3D 向量。然而,直接地,这不允许任何类型的 Eigen 表达式(我们必须为我们使用的每个表达式调用 Eigen::Matrix 构造函数)。因此,如果表达式与 this 一起使用,我们需要创建不必要的临时变量。

建议的解决方案是:

template<typename Derived1, typename Derived2, typename Derived3, typename Derived4, typename Derived5> 
bool planeLineIntersect(const Eigen::MatrixBase<Derived1>& planePoint, 
                        const Eigen::MatrixBase<Derived2>& planeNormal, 
                        const Eigen::MatrixBase<Derived3>& linePoint, 
                        const Eigen::MatrixBase<Derived4>& lineDir,
                        const Eigen::MatrixBase<Derived5>& intersectionPoint)

这并没有透露任何关于预期矩阵的信息,也没有透露哪些参数用于输入和输出,因为我们必须对 intersectionPoint 进行常量转换以允许输出参数中的表达式。据我了解,这是在所有函数参数中允许 Eigen 表达式的唯一方法。尽管不优雅的表达支持,第一个片段对我来说似乎更喜欢。

我的问题:

  1. 您是否认为第二个代码片段是此示例的最佳解决方案?
  2. 您是否曾经对输出参数使用 const-cast 解决方案,或者您认为不值得失去透明度?
  3. 您使用什么准则/最佳实践来编写 Eigen 函数?
4

1 回答 1

1

对于这么小的固定大小的物体,我不会费心去用第一个解决方案。

拥有输出函数参数很少是一个好方法。在您的特定情况下,一种方法是创建一个 PlaneLineIntersection 类,其 ctor 将采用平面和线,存储相交的结果,然后提供访问器来查询计算结果(没有相交,是一个点,一条线)。

顺便说一句,您是否注意到 Eigen/Geometry 模块的 HyperPlane 和 ParametrizedLine 类?ParametrizedLine 类有一个带有 HyperPlane 的 intersectionPoint 成员(尽管它是有限的,因为它假定交叉点确实存在并且它是一个点)。

于 2013-08-26T22:02:31.403 回答