繁体   English   中英

本征矩阵的就地元素类型转换

[英]In-place element type conversion for an Eigen matrix

我想将整数矩阵转换为浮点矩阵,例如:

  1. 数据未复制。
  2. 没有分配新的内存
  3. 数据的新浮点视图是可变的。

最新尝试:

#include "Eigen/Eigen"
#include <iostream>
int main(){
    using namespace Eigen;
    MatrixXi x(3,3);
    x.fill(0);
    double* ptr_x = (double*)(x.data());
    Map<MatrixXd> y(ptr_x, x.rows(), x.cols());
    x(0,0) = 100;
    y = x.cast<double>();
    y(1,1) = 0.5f;
    std::cout << y << "\n";
}

运行时错误:

a.out: malloc.c:2405: 

    sysmalloc: 
        Assertion `(old_top == initial_top (av) && old_size == 0) 
        || ((unsigned long) (old_size) >= MINSIZE 
        && prev_inuse (old_top) 
        && ((unsigned long) old_end & (pagesize - 1)) == 0)' 
    failed.

Aborted (core dumped)

以下内容无法编译:

#include "Eigen/Eigen"
#include <stdint.h>

#include <iostream>
int main(){
    using namespace Eigen;
    MatrixXi x(3,3);
    x.fill(0);
    float* ptr_x = (float*)(x.data());

    Map<MatrixXd> y(ptr_x, x.rows(), x.cols());
    x(0,0) = 100;
    y(1,1) = 0.5f;
    y = x.cast<float>();
    std::cout << y << "\n";
}

我想CastXpr<NewType>::Type可能有效( 文档 )。 但我不知道如何使用它。

CastXpr似乎是unaryExpr如何就地修改一维数组的每个元素?

首先,由于double在内存中为8字节,而int为4字节,因此无法将其转换为double(不分配更多空间)矩阵。

我认为您可以简单地将float指针转换为原始Matrix。 以下代码为我工作。

#include "Eigen/Eigen"
#include <iostream>
int main()
{
    using namespace Eigen;
    MatrixXi x(3, 3);
    x.fill(2);
    MatrixXf* float_ptr = (MatrixXf*) &x;
    float_ptr->operator()(2,2) = 42.1f;

    std::cout << "float cast(2,2): " << 
        float_ptr->operator()(2, 2) << std::endl;
    std::cout << "float cast(1,1): " <<
        float_ptr->operator()(1, 1) << std::endl;
    std::cout << "x(1,1): " << x(1, 1) << std::endl;
}

输出:

float cast(2,2): 42.1
float cast(1,1): 2.8026e-45 (which is ~2)
x(1,1): 2
Press any key to continue . . .

因此...只要使用此指针,分配的对象将充当浮点矩阵,但请记住,由于任何使用'x'的函数调用,您都无法像使用浮点矩阵那样使用'x'将导致分配的内存被解释为整数矩阵

例如:由于我们已将原始(2,2)从int更改为float,如果尝试使用'x'进行检索,则会看到类似以下内容。

    .
    .
    .
    std::cout << "float cast(2,2): " << 
        float_ptr->operator()(2, 2) << std::endl;
    std::cout << "x(2,2): " << x(2, 2) << std::endl;

输出:

float cast(2,2): 42.1
x(2,2): 1109943910

固定类型后,以下内容终于可以使用了。

程序:

#include "Eigen/Eigen"
#include <iostream>
int main(){
    using namespace Eigen;
    MatrixXi x(3,3);
    x.fill(0);
    float* ptr_x = (float*)(x.data());

    Map<MatrixXf> y(ptr_x, x.rows(), x.cols());

    x << 1,2,3,4,5,6,7,8,9;
    y = x.cast<float>();
    y /= 2;
    std::cout << y << "\n";
}

结果:

0.5   1 1.5
  2 2.5   3
3.5   4 4.5

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM