我正在编写一个将 Eigen 表达式模板存储为成员变量的库,以执行它需要执行的复杂计算。但是,似乎我无法存储或返回这些表达式模板,除非它们直接在 MatrixXd 或类似中转换。这迫使每一步都被保存为暂时的,并且破坏了整个设计的效率。
这是一个导致麻烦的简短示例。Holder 只持有一个 Eigen 矩阵,Summer 需要两个持有者,并在调用 get() 时输出它们持有的两个矩阵的总和。当 sum 表达式模板被评估为矩阵时,随后的测试失败(segfault 或 std::bad_alloc)。
包含文件
#ifndef PB_SIMPLE_H
#define PB_SIMPLE_H
#include <Eigen/Dense>
template <class EigenType>
class Holder {
public:
typedef EigenType result_type;
private:
result_type in_;
public:
Holder(const EigenType& in) : in_(in) {}
result_type get() const { return in_; }
};
template <class HoldLeft, class HoldRight>
class Summer {
public:
typedef const typename Eigen::CwiseBinaryOp<
Eigen::internal::scalar_sum_op<double>,
const typename HoldLeft::result_type,
const typename HoldRight::result_type> result_type;
// typedef Eigen::MatrixXd result_type;
private:
HoldLeft left_;
HoldRight right_;
public:
Summer(const HoldLeft& left, const HoldRight& right)
: left_(left), right_(right) {}
result_type get() const { return left_.get() + right_.get(); }
};
typedef Holder<Eigen::MatrixXd> MatrixHolder;
typedef Summer<MatrixHolder, MatrixHolder> MatrixSummer;
#endif /* PB_SIMPLE_H */
简单测试
#include "PbSimple.h"
#include <Eigen/Dense>
int main(int, char * []) {
const unsigned int szx=10,szy=3;
Eigen::MatrixXd x(Eigen::MatrixXd::Constant(szx,szy,1));
MatrixHolder vx(x);
Eigen::MatrixXd y(Eigen::MatrixXd::Constant(szx,szy,2));
MatrixHolder vy(y);
MatrixSummer vsum(vx,vy);
auto expr = vsum.get();
MatrixHolder vz(expr); //force evaluation of sum into new matrix, fails here
return 0;
}
- 在包含文件中,如果您改用注释掉的 typedef,它可以正常工作。
- 我怀疑这个问题是由于一个悬空的参考,但无法证明这一点。