6

我想做的基本上是实现这个功能:

template<typename T>
Matrix<T, Dynamic, Dynamic, ColMajor>* dataToEigen(T* const data, const int rows, const int cols);

无需复制任何数据。我知道完成这样的事情的标准方法是使用地图,但我对这种方法有几个问题。

  1. 我不想重写我的其余代码以接受 Maps 作为输入(即不将 Map 复制到临时矩阵中)。我知道我可以通过泛化我的函数以将 MatrixBase 对象作为输入来做到这一点,但是我在输入中定义了特定的 Matrix 模板是有原因的 - 如果我的函数需要 a Matrix<T, Dynamic, Dynamic, ColMajor>,那是因为只有该类型的矩阵应该用作输入。

  2. 理想情况下,我希望创建的 Matrix 拥有数据指针的所有权,因此我可以通过 shared_ptr 管理 Matrix 而不必再次触摸原始数据指针。

我最初的想法是我可以做一些事情,比如创建一个未初始化的动态大小的 Matrix 对象,然后只设置对象的尺寸和数据指针,但这在 Eigen API 中似乎是不可能的。有谁知道任何解决方法?

4

3 回答 3

3

几乎不可能允许 Eigen::Matrix 直接包装外部缓冲区,这有很多很好的理由,包括 ABI 兼容性、跨动态和静态分配的矩阵的 API 一致性。

一个丑陋的解决方法是定义一个与 MatrixX_ 具有相同布局的结构:

template<typename T> struct Foo {
  T* data;
  DenseIndex rows, cols;
  Matrix<T, Dynamic, Dynamic, ColMajor>& asMatrix() {
    return reinterpret_cast<Matrix<T, Dynamic, Dynamic, ColMajor>&>(*this);
  }
};

另一种解决方案是移至 devel 分支(相当稳定),并使用旨在解决您的确切问题的新Ref<>类等等。它的文档应该足以正确使用它。唯一的困难是您可以轻松地模板化标量类型,因为 Ref<> 不是 Matrix 或 Map 的基类,因此您必须通过显式指定标量类型来调用您的函数,或者创建 Ref< > 复制自己:

foo<T>(M);
foo(Ref<MatrixXd>(M));
于 2013-06-04T23:26:24.557 回答
0

从原始 C/C++ 数组创建特征矩阵?数组的长度是由运行时决定的吗?你可以举我的例子:

float dotproduct_eigen(size_t len, float* va, float* vb)
{
    Eigen::Map<Eigen::Matrix<float, 1, Eigen::Dynamic, Eigen::RowMajor>> vva(va, len);
    Eigen::Map<Eigen::Matrix<float, 1, Eigen::Dynamic, Eigen::RowMajor>> vvb(vb, len);
    float res = vva.dot(vvb);
    return res;
}
于 2021-02-14T14:03:34.197 回答
-1

我认为解决方案很简单,如下所示:

float **data = new float[numRows][numCols];
MatrixXf M(numRows,numCols);
M.data() = data;

默认情况下,Matrix 中的数据按 Column Major 组织,因此如果您希望矩阵以 Row Major 顺序访问 float** 数据,您可以在赋值后转置矩阵。

于 2013-07-01T10:21:10.533 回答