VS2017使用Eigen库
创始人
2025-05-29 02:45:38

在 C++ 中,向量类型通常由库提供。C++ 标准库中的 头文件提供了一个向量容器 std::vector,但它并不是数学意义上的向量类型,而是一种可变大小的数组容器。如果要使用数学意义上的向量类型,可以使用一些常用的数学库,例如:

GLM(OpenGL Mathematics):是一个专门用于 OpenGL 开发的数学库,提供了矩阵、向量、四元数等数学类型,支持常见的数学运算和变换。

Eigen:是一个用于线性代数计算的 C++ 模板库,提供了矩阵、向量、四元数等数学类型,支持高效的数学计算和线性代数运算。

Boost.Geometry:是 Boost 库中的一个几何库,提供了向量、点、线段、射线等几何类型,支持各种几何运算和算法。

这些库都需要在代码中引用相应的头文件和库文件,具体的引用方式和编译方式可能有所不同,需要根据具体的库文档进行设置和配置。

Eigen官方网站:

http://eigen.tuxfamily.org/index.php?title=Main_Page

在VS2017中使用Eigen的两种方式:

  1. https://blog.csdn.net/weixin_45590473/article/details/122857933

  1. https://blog.csdn.net/weixin_42655134/article/details/107414089

通过以下案例,体会Eigen库在C++中的应用

1、在C++中,使用Eigen模板库,用空间中的三个点建立一个新坐标系,通过转移矩阵计算这三个点在新坐标系中的坐标?

思路如下:

a、通过这三个点计算新坐标系的三个轴向量

b、新坐标系的三个轴向量构成的矩阵求逆可以得到转移矩阵

c、用转移矩阵计算新坐标系下点的坐标。

1.1、为什么新坐标系下三个轴向量求逆就是转移矩阵?

在三维空间中,一个坐标系可以由三个不共线的向量构成,分别代表该坐标系的三个轴。对于一个从旧坐标系变换到新坐标系的变换矩阵,我们可以将其表示为一个3x3的矩阵,其中每一列代表新坐标系的一个轴向量在旧坐标系下的坐标表示。

假设我们已经确定了新坐标系的三个轴向量x_axis_new、y_axis_new和z_axis_new,那么我们就可以将它们构成一个3x3的矩阵,记作rotation,即:

Eigen::Matrix3d rotation;
rotation << x_axis_new, y_axis_new, z_axis_new;

由于rotation的每一列都代表新坐标系的一个轴向量在旧坐标系下的坐标表示,因此rotation的逆矩阵就代表了旧坐标系的三个轴向量在新坐标系下的坐标表示。这样,我们就可以将一个向量从旧坐标系变换到新坐标系中,方法是将这个向量表示为一个列向量,然后乘以rotation的逆矩阵,即:

Eigen::Vector3d v_old(x_old, y_old, z_old);
Eigen::Vector3d v_new = rotation.inverse() * v_old;

因此,我们可以使用rotation的逆矩阵作为转移矩阵,将向量从旧坐标系变换到新坐标系中。

1.2、求原坐标系中的点在新坐标系下的坐标,应该用哪种方式?

(1)、求原坐标系中的点在新坐标系下的坐标,可以使用以下两种方式实现:

使用solve()函数:这种方式将新坐标系的三个轴向量作为矩阵的列向量,将原始坐标系中的点作为向量b,解决线性方程组Ax=b,其中x就是点在新坐标系中的坐标。具体地,代码如下:

Eigen::Matrix3d transMat;
transMat.col(0) = axis1_new;
transMat.col(1) = axis2_new;
transMat.col(2) = axis3_new;
Eigen::Vector3d p_old; // 原始坐标系中的点
Eigen::Vector3d origin; // 新坐标系的原点
Eigen::Vector3d p_new = transMat.solve(p_old - origin);

(2)、使用矩阵乘法:这种方式使用一个4x4的变换矩阵T来表示坐标变换,其中前三行表示新坐标系的三个轴向量,最后一行表示新坐标系的原点。将原始坐标系中的点作为一个4维齐次坐标表示,通过矩阵乘法计算得到点在新坐标系中的4维齐次坐标,然后将齐次坐标除以第四个分量得到点在新坐标系中的三维坐标。具体地,代码如下:

Eigen::Matrix4d transform;
transform << axis1_new, 0,axis2_new, 0,axis3_new, 0,origin_new, 1;
Eigen::Vector4d p_old_homog(p_old(0), p_old(1), p_old(2), 1);
Eigen::Vector4d p_new_homog = transform * p_old_homog;
Eigen::Vector3d p_new = p_new_homog.head<3>() / p_new_homog(3);

这两种方式本质上是等价的,但是实现方式略有不同。使用solve()函数更加直观,但是需要显式地解决线性方程组,可能更加耗时。使用矩阵乘法的方式可能更加高效,但需要注意实现中的齐次坐标转换。具体实现方式应根据具体情况选择。

方式(2)中的思路和思路来源参考2中的代码类似

1.3

Eigen::Vector3d newP2 = transMat.solve(p2 - origin);solve函数的使用和下面这句代码有什么不同吗Eigen::Vector3d p2_new = transform * (p2_old - origin_new);

在Eigen中,solve()函数和使用矩阵乘法都可以用于计算一个向量相对于某个新坐标系的坐标。但是,它们的实现方式有所不同。

solve()函数用于解决线性方程组Ax=b,其中A是一个矩阵,b是一个向量,x是一个未知向量,用于计算向量x的值。在Eigen中,solve()函数的调用格式为x = A.solve(b)。

在这个问题中,我们可以将转移矩阵transMat看作是一个线性变换,它将原始坐标系中的向量变换为新坐标系中的向量。那么,如果我们想要计算向量p2相对于新坐标系的坐标,我们可以将其表示为线性方程组Ax=b,其中A是转移矩阵,b是原始向量p2,x是新坐标系中的向量p2_new。因此,我们可以使用solve()函数来计算p2_new的值,如下所示:

Eigen::Vector3d p2_new = transMat.solve(p2 - origin);

另一方面,矩阵乘法可以将一个向量映射到另一个向量,这是另一种实现向量变换的方法。在Eigen中,我们可以使用矩阵乘法来计算一个向量相对于某个新坐标系的坐标。具体地,我们可以使用一个矩阵transform来表示坐标变换,使用向量p2_old来表示原始坐标系中的向量,使用向量origin_new来表示新坐标系的原点。那么,我们可以使用以下代码来计算p2_new的值:

Eigen::Vector3d p2_new = transform * (p2_old - origin_new);

总体上说,solve()函数和矩阵乘法都可以用于计算向量相对于某个新坐标系的坐标,但它们的实现方式有所不同。solve()函数用于解决线性方程组,而矩阵乘法则将向量映射到新坐标系中。在实践中,使用哪种方法取决于具体的应用场景和需求。

1.4、思路来源参考

  1. https://stackoverflow.com/questions/49769459/convert-points-on-a-3d-plane-to-2d-coordinates/49771112#49771112

  1. https://stackoverflow.com/questions/68506084/i-have-a-plane-between-3-points-and-want-to-get-a-transformation-matrix-which-al

  1. https://stackoverflow.com/questions/52154004/problem-superimposing-and-aligning-3d-triangles/52163563#52163563

  1. https://math.stackexchange.com/questions/1983054/using-3-points-create-new-coordinate-system-and-create-array-of-points-on-xy

1.5、右手定则确定空间坐标系

http://www.gaosan.com/gaokao/262408.html

2、代码实践

#include 
#include 
using namespace Eigen;
using namespace std;using Eigen::Matrix3d;// 三个点的坐标信息
//Vector3d p1(1.0, 2.0, 3.0);
//Vector3d p2(4.0, 5.0, 6.0);
//Vector3d p3(7.0, 8.0, 9.0);Vector3d p1(1.0, 0.0, 0.0);
Vector3d p2(0.0, 1.0, 0.0);
Vector3d p3(0.0, 0.0, 1.0);Vector3d p4(0.5, 0.5, 0.0);int main()
{//求新坐标的三个轴向量Eigen::Matrix3d transMat;transMat.col(0) = (p2 - p1).normalized();std::cout << transMat.col(0) << std::endl;transMat.col(2) = transMat.col(0).cross((p3 - p1)).normalized();std::cout << transMat.col(2) << std::endl;transMat.col(1) = transMat.col(2).cross(transMat.col(0));std::cout << transMat.col(1) << std::endl;//求转移矩阵,新坐标的三个轴向量求逆就是转移矩阵Eigen::Matrix3d transform1 = transMat.inverse();//求点在新坐标系下的坐标Eigen::Vector3d origin = p1;Eigen::Vector3d newP1 = Eigen::Vector3d::Zero();Eigen::Vector3d newP2 = transform1 * (p2 - origin);Eigen::Vector3d newP3 = transform1 * (p3 - origin);Eigen::Vector3d newP4 = transform1 * (p4 - origin);std::cout << newP1 << std::endl;std::cout << newP2 << std::endl;std::cout << newP3 << std::endl;std::cout << newP4 << std::endl;}

3、经验证,该代码可以求出原坐标系中的点在新坐标系下的坐标。

上一篇:MySQL-->上篇

下一篇:Web文件下载总结

相关内容

热门资讯

SpringBoot的单例模式... 目录 Spring使用的设计模式 单例模式简介 Spring所管理的注解 Spring获取对象时加...
小米总裁:一个能打SU7的对手... 5月27日,小米集团总裁、小米品牌总经理卢伟冰在小米一季度业绩电话会上表示,“SU7发布这么久,一款...
港股创新药ETF(159567... 5月30日,港股医药股走强,石药集团涨近8%,消息面上,石药集团在港交所公告,集团目前正与若干独立第...
2023年“网络安全”赛项江苏... 2023年中职组江苏省淮安市“网络空间安全”赛项 ①.2023年中职组江苏省淮安市任务书②.2023...
ArcGIS: 如何利用模型构... 01 实验数据说明chengdu.pix(栅格图像),其中...
从对标星巴克到沦为 “小透明”... 来源 | 伯虎财经(bohuFN)作者 | 林恩凭借“茶饮+烘焙”的双品类模式与对空间体验的执着追求...
图形视图框架QGraphics... QGraphicsScene 该类充当 QGraphicsItems 的容器。它与 QGraphic...
A股三大指数低开 CPO概念跌...   中新经纬5月30日电 30日早间,A股三大指数集体低开,上证指数跌0.14%,报3358.81点...
广东虎门通报小车高架坠桥5人死... 近日,广东东莞环莞快速路虎门段的一起交通事故引发了广泛关注。5月19日,有网友反映其侄儿驾车经过该路...
全球资产再平衡,港股创新药赛道... 近年来,全球资本市场的结构性调整愈发显著。在美联储加息周期临近尾声、地缘博弈常态化背景下,资金正重新...
警惕信创ETF高溢价风险 摘要: 海光信息和中科曙光计划进行资产重组,持有这两只股票权重较高的信创ETF(159537)受到市...
Spring Boot/Clo... 一、前言 随着微服务的流行,服务和服务之间的稳定性变得越来越重要。 Sentinel ...
新思科技:在中国市场销售芯片设... 当地时间5月29日,新思科技称已收到美国商务部工业和安全局 (BIS) 信函,告知新思科技与中国相关...
TIME_WAIT 尽可能客户... 、LISTENING状态   FTP服务启动后首先处于侦听(LISTENING...
蓝桥杯 - 皮亚诺曲线距离 题目描述 皮亚诺曲线是一条平面内的曲线。 下图给出了皮亚诺曲线的 111 阶情形,它是...
卖枕头,真能救酒店? 酒店卖枕... 定焦One(dingjiaoone)原创见习作者 | 何欣欣编辑 | 金玙璠在行业整体规模狂飙突进的...
手写-签名的隐私政策 本应用尊重并保护所有使用服务用户的个人隐私权。为了给您提供更准确、更有个性化的服务,本...
给车机投放广告?深蓝汽车CEO... 文 / 零度来源 / 节点财经5月27日晚间,深蓝汽车在其官方微博账号发文称,“今日,我们关注到部分...
ElasticSearch-第... 目录 ElasticSearch简介 ElasticSearch 应用场景 ElasticSearc...
JAVA练习82-在排序数组中... 提示:文章写完后,目录可以自动生成,如何生成可参考右边的帮...
最大值最小值归一化_sklea...  然后我们再来看一下,再来说一下归一化 比如:在公司有两个人,一个是W2 他能力强,然后领导给他分配...
中金公司:微盘风格未来可能仍有... 中金公司研报称,展望未来,微盘风格可能呈现优势边际弱化、仍存在一定结构性机会的格局。政策端对科创小微...
【超详细】MMLab分类任务m... 本文详细介绍了使用MMLab的mmclassification进行分类任务的环境配置、训练与预测流程...
内地优质科技企业“排大队”赴港... 科技企业纷纷涌向港股市场。Wind资讯数据显示,截至5月29日,有5家企业聆讯通过,另有155家企业...
Spring学习(三) Spring的AOP的XML开发(重要指数五颗星*****) 一、AOP...
原创 今... 在1998年房改后,我国房地产市场经历了一次爆发式增长,许多购房者借此机会实现了财富的快速增值,尤其...
原创 A... 5月30日,新股打新市场迎来影石创新的发行申购。它在网上发行656万股,顶格申购需配沪市股票市值6....
15个新一线城市名单出炉,郑州... 【大河财立方 记者 程帅星】5月28日,第一财经旗下新一线城市研究所发布《2025新一线城市魅力排行...
Vector底层源码解析 Java源码系列:下方连接 http://t.csdn.cn/Nwzed 文章目录...
月内3家券商定增迎来新进展,加... 前,证券行业的竞争愈发激烈,资本实力成为券商在市场竞争中制胜的关键因素。近期,证券行业再融资事项迎来...