首页 > 解决方案 > Eigen 自定义表达式类型(或 CWise Op 仿函数?)

问题描述

考虑这个简单的函数(一种伪代码):

template <typename Derived>
void f (const MatrixBase<Derived>& input1,
        const MatrixBase<Derived>& input2,
        const MatrixBase<Derived>& input3,
        Vec6& output)
{
    part1(output) = <an expr using the three inputs>;
    part2(output) = <another expr using the three inputs>;
}

其中part1part2是分别选择 的前 3 行和后 3 行的块表达式output。我知道这output始终是一个具有 6 个系数的列向量。

我想避免传递output论点。但我也想避免返回一个明确的Vec6,以避免临时副本。

因此,我想返回那些神奇的特征表达式对象之一,它只存储对输入的引用,并且实际上只在需要时才进行计算。

我的问题:

  1. 这值得么?鉴于它是一个“小”的 6 维向量(例如,文档说使用小的 3 维向量,编译器通常能够优化掉临时变量,因此避免它们没有多大意义)

  2. 我可以使用自定义函子实现我的返回表达式类型,CWiseNullaryOp还是我真的需要自定义表达式类型?

谢谢


编辑:所以我们确定临时对象已被优化(见评论);这回答了问题 1,并使问题 2 不相关。

但是,为了好奇和更多地了解 Eigen,是否有人对我的函数的可行表达式类型有一些提示?(假设值得设计一个)

标签: c++eigen

解决方案


假设 Vec6 的设计“正确”(参见例如 Rule Of Zero),那么如果您的函数f()采用以下形式

Vec6 f(const MatrixBase<Derived>& input1,
       const MatrixBase<Derived>& input2,
       const MatrixBase<Derived>& input3)
{
    Vec6 answer;

    //Manipulate answer
    //...

    return answer; 
}

然后在大多数现代编译器上启用优化后,不会发生复制。在此处查看有关返回值优化的 Wikipedia 部分。

(要使用您的对象和编译器测试该理论,您可以将 Vec6 包装在您自己的类中,让所有构造函数在执行时打印出来,并检查您是否获得了预期的构造函数调用次数。)


推荐阅读