我是靠谱客的博主 端庄水杯,最近开发中收集的这篇文章主要介绍Eigen有哪些需要注意的操作Eigen有哪些需要注意的操作,觉得挺不错的,现在分享给大家,希望可以做个参考。

概述

Eigen有哪些需要注意的操作

  • Eigen有哪些需要注意的操作
    • 1. Eigen有哪些行操作,列操作,块操作,怎样写会更高效?
    • 2. ColMajor和RowMajor是什么?Eigen默认的是哪种?
    • 3. noalias()和eval()方法是做什么的?
    • 4. 如何使用Eigend求解Ax=b?有几种方法?
    • 5. 如何使用Eigen对矩阵做QR分解?Householder/Givens Rotation?
    • 6. Eigen::Quaternion有哪几种构造方法?其内部x,y,z,w的顺序是怎么样的?
    • 7. 把矩阵、四元数或者包含矩阵、四元数的结构体放入STL容器需要注意什么?

Eigen有哪些需要注意的操作

1. Eigen有哪些行操作,列操作,块操作,怎样写会更高效?

行操作:

matrix.row(n);
matrix.topRows(n);
matrix.bottomRows(n);

列操作:

matrix.col(n);
matrix.leftCols(n);
matirx.rightCols(n);

块操作:
动态矩阵版本:

matrix.block(i,j,m,n);	// 大小为(m,n),起始于(i,j)
matrix.topLeftCorner(m,n);
matrix.bottomLeftCorner(m,n);
matrix.topRightCorner(m,n);
matrix.bottomRightCorner(m.n);

固定矩阵版本:

matrix.block<m,n>(i,j);	// 大小为(m,n),起始于(i,j)
matrix.topLeftCorner<m,n>();
matrix.bottomLeftCorner<m,n>();
matrix.topRightCorner<m,n>();
matrix.bottomRightCorner<m.n>();

Eigen官方文档上给出两个建议:
(1) 固定矩阵版本的block在运行时效率更高,但在编译是消耗的时间会更多;
(2) 在写代码时要让Eigen知道尽可能多的信息,例如,如果是取一行操作就使用.col()操作,而不要使用.block()操作

2. ColMajor和RowMajor是什么?Eigen默认的是哪种?

ColMajor指按行优先存储,RowMaor指按列有限存储,默认是列有限
补充:
(1) 如果要和其他库合作开发,为了转化方便,可以选择同样的存储方式;
(2) 应用中设计大量行遍历操作,应该有限选择行有限,寻址更快;
(3) 默认是列有限,而且大多库是按照这个顺序的;

3. noalias()和eval()方法是做什么的?

当相同的Matirx或者Array同时为等式的左值和右值时,容易出现混淆:
(1) 组件级别的操作不会出现混淆,例如matrix加法、scalar乘法、array乘法等,但是matrix乘法会出现混淆,而Eigen会默认解决混淆问题,如果你认为不会出现混淆,那么可以使用noalias()提高效率:
matB.noalias() = matA * matA;
(2) 如果混淆出现时,可以使用eval()函数解决,该函数会引入临时变量以避免混淆:
matA = (matA*matB).eval();

4. 如何使用Eigend求解Ax=b?有几种方法?

一共有五种方法:
(1) 直接求逆:

x = A1.inverse()*b1;

(2) 采用QR分解求求解:

x = A1.colPivHouseholderQr().solve(b1);	 // 速度:+    精度:++
x = A1.fullPivHouseholderQr().solve(b1); // 速度:-    精度:+++

(3)采用LU分解求解:

x = A1.partialPivLu().solve(b1);         // 速度:++   精度:+
x = A1.fullPivLu().solve(b1);            // 速度:-    精度:+++

(4)采用LLT分解求解:

x = A1.llt().solve(b1);                  // 速度:+++  精度:+

(5)采用LDLT分解求解:

x = A1.ldlt().solve(b1);                 // 速度:+++  精度:++

5. 如何使用Eigen对矩阵做QR分解?Householder/Givens Rotation?

(1)Householder进行QR分解:
HouseholderQR qr;
qr.compute(A);
MatrixXd R = qr.matrixQR().triangularViewEigen::Upper();
MatrixXd Q = qr.householderQ();

(2)Givens Rotation进行QR分解:
使用Givens Rotation进行QR分解的过程是通过Givens矩阵将待分解的矩阵从左下角开始逐渐消零为0的过程,在Eigen中没有找到直接的实现,可能是要手撸这个过程,可以参考https://zhuanlan.zhihu.com/p/136551885

6. Eigen::Quaternion有哪几种构造方法?其内部x,y,z,w的顺序是怎么样的?

Eigen::Quaternion内部的顺序为w,x,y,z

从官网上看构造有如下几种方式:
(0) 默认构造

Quaternion ()

(1) 直接赋值

Quaternion (const Scalar &w, const Scalar &x, const Scalar &y, const Scalar &z)

(2) 从旋转矩阵构造

Quaternion (const MatrixBase< Derived > &other)

(3) 从轴角构造

Quaternion (const AngleAxisType &aa)

(4) 从数组构造

Quaternion (const Scalar *data)

(5) 从其他旋转向量构造

Quaternion (const Quaternion< OtherScalar, OtherOptions > &other)
Quaternion (const QuaternionBase< Derived > &other)

7. 把矩阵、四元数或者包含矩阵、四元数的结构体放入STL容器需要注意什么?

对Eigen中的固定大小的类使用STL容器的时候,如果直接使用就会出错,例如

std::map<int, Eigen::Vector4f>
std::vector<Eigen::Vector2d>

原因是固定大小的类是指在编译过程中就已经分配好内存空间的类,为了提高运算速度,对于SSE或者AltiVec指令集,向量化必须要求向量是以16字节对齐的方式分配内存空间,所以针对这个问题,容器需要使用Eigen自己定义的内存分配器,即aligned_allocator。因此正确的写法是:

std::map<int, Eigen::Vector4f, Eigen::aligned_allocator<std::pair<const int, Eigen::Vector4f>>
std::vector<Eigen::Vector2d,Eigen::aligned_allocator<Eigen::Vector2d>>

此外,对其他SLAM算法感兴趣的同学可以看考我的博客SLAM算法总结——经典SLAM算法框架总结

最后

以上就是端庄水杯为你收集整理的Eigen有哪些需要注意的操作Eigen有哪些需要注意的操作的全部内容,希望文章能够帮你解决Eigen有哪些需要注意的操作Eigen有哪些需要注意的操作所遇到的程序开发问题。

如果觉得靠谱客网站的内容还不错,欢迎将靠谱客网站推荐给程序员好友。

本图文内容来源于网友提供,作为学习参考使用,或来自网络收集整理,版权属于原作者所有。
点赞(50)

评论列表共有 0 条评论

立即
投稿
返回
顶部