描述

使用C++语言的Eigen库进行一些常见操作

使用库时,请一定注意两点

  1. 定义清楚矩阵类型
  2. 矩阵乘法注意尺寸对应

代码

头文件声明

#include <Eigen/Dense>

1. 矩阵声明

  • n*n方阵(已知n)

    Eigen::Matrix2d m_matrix;
    m_matrix<< 2,3,2.2,1;
    std::cout << "m_matrix = \n"<< m_matrix<std::endl;
    

    注意矩阵里的值有2.2这个浮点型,因此定义Eigen::Matrix2i会出现问题(Matrix2i代表整数)

  • m*n方阵(已知m和n)

    Eigen::MatrixXd xx(5,2);
    xx << 2,3,2.2,1,2,3,2,1,2,3;
    
  • 零矩阵

    Eigen::MatrixXf m_matrix = Eigen::MatrixXf::Zero(5,5);
    
    Eigen::MatrixXf m_matrix = Eigen::MatrixXf::Zero(5,2);
    
  • 对角矩阵

    Eigen::MatrixXf m_matrix = Eigen::MatrixXf::Identity(5,5);
    
    Eigen::MatrixXf m_matrix = Eigen::MatrixXf::Identity(2,5);
    

2. 矩阵的大小

int cols = m_matrix.cols();
int rows = m_matrix.rows();
std::cout<<cols<<std::endl;
std::cout<<rows<<std::endl;

3. 矩阵常见操作

  • 操作矩阵元素

    m_matrix(1,1) = 2;
    
  • 乘法
    
    m_matrix = A * B;
    

    矩阵A和矩阵B,应该满足 mn尺寸与nk尺寸,矩阵m_matrix的尺寸应为m*k

  • 矩阵赋值
    A = B;
    

    矩阵A和矩阵B需要尺寸一致

4. 矩阵绝对值和最大元素

矩阵里的每个元素求绝对值
eigen中矩阵是无法直接对矩阵操作,让每个元素都求绝对值的。
但是可以通过转化为Array类型来操作。

  • matrix转为array: .array()
  • array转为matrix:.matrix()
  • 求绝对值
    Eigen::MatrixXf x;
    Eigen::ArrayXXf x_abs = x.array().abs();
    
  • 求矩阵绝对值后的最大元素
    Eigen::MatrixXf x;
    Eigen::ArrayXXf x_abs = x.array().abs();
    float max_value = x_abs.maxCoeff();
    

5. 矩阵转置和矩阵求逆

  • 转置
Eigen::MatrixXf m_matrix;
Eigen::MatrixXf m_matrix_T;
m_matrix_T = m_matrix.transpose();
  • 逆矩阵
Eigen::MatrixXf m_matrix;
Eigen::MatrixXf m_matrix_inv;
m_matrix_inv = m_matrix.inverse();

6. 向量截取

Eigen::VectorXf pc_mean;
pc_mean.resize(4);
pc_mean<<1, 2, 3.3, 4.4;
Eigen::Vector3f seeds_mean = pc_mean.head<3>();// .head<n>,取数组前n个数std::cout<<pc_mean<<std::endl;
std::cout<<seeds_mean<<std::endl;

7. 矩阵的特征值和特征向量

  • 特征值

    Eigen::Matrix2d m_matrix;
    m_matrix << 2,3,2.2,1;
    Eigen::EigenSolver<Eigen::Matrix2d> eigen_solver ( m_matrix );
    Eigen::MatrixXd eig_value = eigen_solver.pseudoEigenvalueMatrix();
    std::cout << "matrix values = \n" <<eig_value<<std::endl;
    

    输出为2*2的对角矩阵,对角线上的值就是特征值,也就是4.11725和-1.11725

    matrix values =
    4.11725        00 -1.11725
    
  • 特征向量

    Eigen::Matrix2d m_matrix;
    m_matrix << 2,3,2.2,1;
    Eigen::EigenSolver<Eigen::Matrix2d> eigen_solver ( m_matrix );
    Eigen::MatrixXd eig_vector = eigen_solver.pseudoEigenvectors();
    std::cout << "matrix vectors = \n" <<eig_vector<<std::endl;
    std::cout << "matrix vectors(1,0) = \n" <<eig_vector(1,0)<<std::endl;
    

    输出是

    matrix vectors =
    0.817019 -0.701478
    0.576611  0.728894
    matrix vectors(1,0) =
    0.576611
    
  • 特征值与特征向量的使用

    我们都知道特征值和特征向量是成对出现的。他们能形成关系:

    我们有一个矩阵A,其特征值λ 和 特征向量 v 的关系是
    A * V = λ * v

    可以用代码验证,还是用之前的矩阵

    // 取出全部的特征值
    Eigen::MatrixXd new_value = Eigen::MatrixXd::Zero(rows,1);
    for (int i = 0 ; i < rows; i++)
    {new_value(i,0) = eig_value(i,i);
    }
    std::cout<<new_value<<std::endl;
    // 取出对应第一个特征值的特征向量
    Eigen::MatrixXd new_vector = Eigen::MatrixXd::Zero(rows,1);
    for (int i = 0 ; i < rows; i++)
    {new_vector(i,0) = eig_vector(i,0);
    }
    std::cout<<new_vector<<std::endl;// 观察第一个特征值和其对应特征向量的乘积
    std::cout<<"A * V = \n"<<m_matrix*new_vector<<std::endl;
    std::cout<<"lambda * V= \n"<<new_value(0,0)*new_vector<<std::endl;
    

    结果是

    // 特征值,就是特征值矩阵的对角元素
    4.11725
    -1.11725
    // 第一个特征值的特征向量,就是特征向量矩阵的第一列
    0.817019
    0.576611
    // 我们发现结果是相同的
    A * V =
    3.36387
    2.37405
    lambda * V=
    3.36387
    2.37405
    
  • 只是能输出(代码里怎么可能只是想打印一下呢,所以请你只看第一条)

    Eigen::Matrix2d m_matrix;
    m_matrix << 2,3,2.2,1;
    Eigen::EigenSolver<Eigen::Matrix2d> eigen_solver ( m_matrix );
    std::cout << "matrix values = \n" << eigen_solver.eigenvalues() << std::endl;
    std::cout << "matrix vectors = \n" << eigen_solver.eigenvectors() << std::endl;
    

    输出为

    matrix values = (4.11725,0)
    (-1.11725,0)
    matrix vectors = (0.817019,0) (-0.693426,0)(0.576611,0)  (0.720528,0)
    

调试经验

在使用Eigen库的时候,总是会出现一些错误,主要长成下面这样,或者一些没有提示错误位置的bug

static_assert failed due to requirement'Eigen::internal::has_ReturnType<ScalarBinaryOpTraits<typenameActualDstTypeCleaned::Scalar, typenameCwiseNullaryOp<scalar_constant_op<float>, Matrix<float, -1, -1, 0, -1, -1>>::Scalar, assign_op<double, float> > >::value'"YOU_MIXED_DIFFERENT_NUMERIC_TYPES__YOU_NEED_TO_USE_THE_CAST_METHOD_OF_MATRIXBASE_TO_CAST_NUMERIC_TYPES_EXPLICITLY"EIGEN_CHECK_BINARY_COMPATIBILIY(Func,typename ActualDstTypeCleaned::Scalar,typename Src::Scalar);^~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
/Users/admin/Desktop/CodeBase/c++_try/Eigen/src/Core/util/XprHelper.h:859:3: note: expanded from macro 'EIGEN_CHECK_BINARY_COMPATIBILIY'EIGEN_STATIC_ASSERT((Eigen::internal::has_ReturnType<ScalarBinaryOpTraits<LHS, RHS,BINOP> >::value), \^~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
/Users/admin/Desktop/CodeBase/c++_try/Eigen/src/Core/util/StaticAssert.h:33:40: note: expanded from macro 'EIGEN_STATIC_ASSERT'#define EIGEN_STATIC_ASSERT(X,MSG) static_assert(X,#MSG);^             ~
/Users/admin/Desktop/CodeBase/c++_try/Eigen/src/Core/PlainObjectBase.h:797:17: note: in instantiation of function template specialization'Eigen::internal::call_assignment_no_alias<Eigen::Matrix<double, -1, -1,0, -1, -1>,Eigen::CwiseNullaryOp<Eigen::internal::scalar_constant_op<float>,Eigen::Matrix<float, -1, -1, 0, -1, -1> >,Eigen::internal::assign_op<double, float> >' requested hereinternal::call_assignment_no_alias(this->derived(), other.derived(...^
/Users/admin/Desktop/CodeBase/c++_try/Eigen/src/Core/PlainObjectBase.h:602:7: note: in instantiation of function template specialization'Eigen::PlainObjectBase<Eigen::Matrix<double, -1, -1, 0, -1, -1>>::_set_noalias<Eigen::CwiseNullaryOp<Eigen::internal::scalar_constant_op<float>,Eigen::Matrix<float, -1, -1, 0, -1, -1> > >' requested here_set_noalias(other);^
/Users/admin/Desktop/CodeBase/c++_try/Eigen/src/Core/Matrix.h:423:9: note: ininstantiation of function template specialization'Eigen::PlainObjectBase<Eigen::Matrix<double, -1, -1, 0, -1, -1>>::PlainObjectBase<Eigen::CwiseNullaryOp<Eigen::internal::scalar_constant_op<float>,Eigen::Matrix<float, -1, -1, 0, -1, -1> > >' requested here: Base(other.derived())^
/Users/admin/Desktop/CodeBase/c++_try/1.cpp:100:33: note: in instantiation offunction template specialization 'Eigen::Matrix<double, -1, -1, 0, -1,-1>::Matrix<Eigen::CwiseNullaryOp<Eigen::internal::scalar_constant_op<float>,Eigen::Matrix<float, -1, -1, 0, -1, -1> > >' requested hereEigen::MatrixXd new_value = Eigen::MatrixXf::Zero(rows,1);^
1 error generated.
make[2]: *** [CMakeFiles/s.dir/1.o] Error 1
make[1]: *** [CMakeFiles/s.dir/all] Error 2
make: *** [all] Error 2

出现过很多次,每次的解决办法都是
要么我写错了矩阵的类型,类型A赋值给了类型B;要么就是矩阵乘法的尺寸不对应。
这都是低级的错误。

附录

  • 几种声明类型
    Matrix:
    Matrix2cd:
    Matrix2cf:
    Matrix2d:
    Matrix2f:
    Matrix2i:
    Matrix2Xcd:
    Matrix2Xcf:
    Matrix2Xd:
    Matrix2Xf:
    Matrix2Xi:

  • 将2替换成3、4、X,会有相同的声明类型

没有深研究,简单来说,数字代表nn方阵的大小,‘X’代表这个矩阵不是方阵,是一个mn的矩阵,‘d’代表double,‘f’代表float, ‘i’代表整数,‘c’代表complex,即复数;’d’表示dynamic,即表示矩阵中有些维数是不确定的,动态的……

举例子比如说:Matrix2cd,表示的是2*2维的,其每个元素都是复数,复数的实部和虚部都为double类型。

C++Eigen库矩阵常见操作相关推荐

  1. Eigen教程:1 Eigen简介和矩阵常见操作

    文章目录 一. 模块和头文件 二. 矩阵 1. 矩阵类型 2. 数据存储 3. 动态矩阵和静态矩阵 4. 矩阵元素的访问 5. 设置矩阵的元素 6. 重置矩阵大小 7. 矩阵和向量的算术运算 8. 行 ...

  2. python lib库_python标准库pathlib常见操作

    pathlib-- 面向对象的文件系统路径 它是python3.4新增的一个标准库,提供了不同操作系统下文件系统路径的操作方式,有两大类一个是纯路径不带I/0操作,另一个可以进行I/0的类.pathl ...

  3. Eigen库矩阵的求逆函数无法在CUDA代码使用

    VS2019+Eigen3.3.9+CUDA11.9编译OpenMVS2.0遇到以下报错 calling a __host__ function("Eigen::MatrixBase< ...

  4. python数值运算实例_Python矩阵常见运算操作实例总结

    本文实例讲述了Python矩阵常见运算操作.分享给大家供大家参考,具体如下: python的numpy库提供矩阵运算的功能,因此我们在需要矩阵运算的时候,需要导入numpy的包. 一.numpy的导入 ...

  5. python矩阵运算_Python矩阵常见运算操作实例总结

    本文实例讲述了Python矩阵常见运算操作.分享给大家供大家参考,具体如下: python的numpy库提供矩阵运算的功能,因此我们在需要矩阵运算的时候,需要导入numpy的包. 一.numpy的导入 ...

  6. python矩阵运算实例_Python矩阵常见运算操作实例总结 python 怎么实现矩阵运算

    python 怎么查看一个矩阵的维数你是知道的,等你,我已经栖息了疲惫的憧憬,夜夜抚慰残梦的翅膀. 都是复制党,百度知道回答真的质量太低了,真的很心疼,言归正传 利用numpy分享矩阵维数: impo ...

  7. python矩阵运算实例_Python矩阵常见运算操作实例总结

    本文实例讲述了python矩阵常见运算操作.分享给大家供大家参考,具体如下: python的numpy库提供矩阵运算的功能,因此我们在需要矩阵运算的时候,需要导入numpy的包. 一.numpy的导入 ...

  8. Python 数据分析三剑客之 NumPy(六):矩阵 / 线性代数库与 IO 操作

    CSDN 课程推荐:<Python 数据分析与挖掘>,讲师刘顺祥,浙江工商大学统计学硕士,数据分析师,曾担任唯品会大数据部担任数据分析师一职,负责支付环节的数据分析业务.曾与联想.亨氏.网 ...

  9. matlab和Eigen库中的一些旋转矩阵(方向余弦矩阵)、四元数和欧拉角之间的转换和绘图的注意事项

    最近用matlab和Eigen库中的一些旋转矩阵(方向余弦矩阵).四元数和欧拉角之间的转换和绘图,弄得我有些头疼,把遇到的问题记录一下,以防以后又脑阔疼....有不同的理解可以再评论区批评指正- 主要 ...

最新文章

  1. 技术图文:进一步完善自动化交易系统 - 03
  2. 独家 | 基于新闻标题的股价走势分析(附链接)
  3. 使用Configuration Manager管理移动设备
  4. 基本概念-编写第一个C程序
  5. JavaScript——易班优课YOOC课群在线测试自动答题解决方案(二十一)禁止打开控制台解决方案
  6. MySQL Server has gone away报错原因汇总
  7. Java Enum 枚举
  8. 基于深度卷积神经网络的大豆叶斑病识别
  9. Listings of System and Object Privileges--系统和对象权限列表
  10. 空心心形图案的c语言程序,C语言写的各种心形图案_6583
  11. 【算法笔记】初识离散化
  12. 网络编程技术(技术总结)
  13. 21接力题典1800 数一 重积分 P46 T18
  14. dBm与功率(w)换算关系
  15. Python学习(52周存钱)
  16. java kpi_KRA与KPI 绩效考核
  17. Photoshop:教你快速绘制一把扇子
  18. [转载]常用自动挂机APP下载
  19. 云端地球新会员重磅上线,快来解锁最全权益地图!
  20. 史上最通俗,彻底搞懂字符乱码问题的本质

热门文章

  1. Python:whl安装包简介与制作
  2. 个人博客如何选择虚拟主机
  3. WXML和HTML的区别
  4. Zookeeper(2) - 配置详解与启动原理
  5. R语言数学建模(1):Regression analysis
  6. 【开发教程9】疯壳·人形街舞机器人-整机代码
  7. 转:oracle ocp 指南
  8. CISSP第二章 信息安全治理与风险管理
  9. JS将秒数换算成时分秒 以及转化为年月日 时分秒以及多长时间以前
  10. 用数字签名实现防篡改