【问题标题】:Disable temporary binding of Eigen expression to const references禁用 Eigen 表达式到 const 引用的临时绑定
【发布时间】:2016-01-17 01:31:32
【问题描述】:

我正在尝试编写一个只接受通过const 引用传递的左值特征表达式的函数。我的第一个想法是只保留const Eigen::MatrixBase<Derived>&delete 的过载Eigen::MatrixBase<Derived>&&。令我惊讶的是,deleted 函数不是重载候选集的一部分。所以我尝试了下面的代码

#include <iostream>
#include <Eigen/Dense>

#define PRINT_MY_NAME std::cout << __PRETTY_FUNCTION__ << '\n'

template<typename Derived>
void f(const Eigen::MatrixBase<Derived>&) // (1)
{
    PRINT_MY_NAME;
}

template<typename Derived>
void f(Eigen::MatrixBase<Derived>&&)      // (2)
{
    PRINT_MY_NAME;
}

int main()
{
    Eigen::MatrixXd A;

    f(A);     // invokes (1)
    f(A + A); // invokes also (1) !!!
}

哪个输出(gcc5.2)

void f(const Eigen::MatrixBase&) [with Derived = Eigen::Matrix ]

void f(const Eigen::MatrixBase&) [with Derived = Eigen::CwiseBinaryOp , const Eigen::Matrix , const Eigen: :矩阵 >]

显然没有考虑右值重载。我现在很清楚第二个不是更好的匹配,因为我传递了一个右值 Eigen 表达式,它可以转换为 Eigen::MatrixBase&lt;&gt;,但不是完全相同的类型。现在是我的问题:

  • 如何禁用或检测作为f 参数传递的右值特征表达式?问题是表达式可以具有任意类型(Eigen 使用表达式模板),例如 CwiseBinaryOp&lt;...CwiseBinaryOp&lt;...&gt;&gt; 等等。这是一个更大问题的一部分,其中我有一个类似于 make 的实用程序函数,它接受一个左值并将其绑定到类中的 const 引用表达式。如果表达式是一个右值,那么所有的赌注都是关闭的,因为引用绑定不是通过构造函数参数传播的,所以我想禁止传递右值 Eigen 表达式。

【问题讨论】:

  • 有趣,我在尝试做一个最小的例子时没有相同的result
  • @PiotrSkotnicki 是的,这可能就是为什么不考虑第二次重载的原因。问题是我该如何执行?
  • @MatthieuM。我相信这与 Eigen 的“胆量”以及它如何实现表达式模板有关。您是否也尝试过上面的确切代码?如果您被调用 (2),我会感到非常惊讶。
  • 我没有 Eigen,它在我知道的在线编译器上不可用,所以不,我没有用 Eigen 进行测试。不过,无论如何它应该是可归约的。

标签: c++ c++11 eigen rvalue-reference eigen3


【解决方案1】:

我想我发现了发生了什么:表达式模板 A + A 的结果是 const,因此存在 CV 不匹配。将const 添加到第二个重载就可以了:

template<typename Derived>
void f(const Eigen::MatrixBase<Derived>&&)      // (2)
{
    PRINT_MY_NAME;
}

【讨论】:

  • 该死......他们没有得到const的返回类型很臭的备忘录吗:x
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 2019-07-02
  • 2013-07-04
  • 1970-01-01
  • 2012-07-18
  • 2018-08-14
  • 2021-09-09
  • 2016-11-09
相关资源
最近更新 更多