c++ 矩阵应用

matrix与vector

使用二维数组(matrix):

  • 静态大小
    二维数组的大小在编译时确定,无法动态改变。这意味着你需要在定义时指定行数和列数,并且在程序运行时无法调整这些维度。
  • 简单直观:
    对于固定大小的矩阵,使用二维数组可能更加简单和直观。访问元素时使用matrix[i][j]的语法比较直接。
  • 内存布局:
    二维数组的内存布局是连续的,这可能有利于一些性能优化,尤其是在大型数据集上的操作。
  • 缺点:
    静态大小是二维数组的一个限制,如果需要动态调整矩阵的大小,使用二维数组就不再适用。

使用std::vector<std::vector>:

  • 动态大小:
    std::vector允许动态分配内存,并且可以在运行时动态调整大小,包括行和列数。这使得它更加灵活,能够处理动态变化的数据需求。
  • 灵活性:
    可以通过push_back()、resize()等函数动态地添加行和列,或者改变现有行和列的大小。这对于需要动态处理数据的情况非常有用。
  • 通用性:
    std::vector是标准库提供的通用容器,它提供了更多的功能和算法支持,如排序、查找等操作,而不仅仅局限于矩阵操作。
  • 缺点:
    内存布局可能不是连续的,尤其是对于std::vector<std::vector>来说,每个std::vector在内存中是分开存储的,这可能导致访问效率略有降低。
  • 选择适当的场景:
    固定大小的矩阵:如果矩阵的大小在编译时已知且不会变化,使用二维数组可能更合适,因为它更简单和直接。 动态大小的矩阵:如果矩阵的大小需要在运行时动态调整,或者需要使用std::vector提供的其他灵活性和算法支持,那么std::vector<std::vector>更适合,尽管在性能上可能会稍有损失。

  • 性能要求:如果性能是关键问题,尤其是对于大型数据集和复杂的数学运算,可以考虑使用专门的线性代数库如Eigen或Armadillo,它们在性能和功能上都有优势。

综上所述,选择二维数组还是std::vector<std::vector< T >>取决于你的具体需求,包括矩阵的大小是否固定、是否需要动态调整大小以及对性能和灵活性的需求。

矩阵操作

  1. 使用二维数组
#include <iostream>
using namespace std;int main() {const int rows = 3;const int cols = 3;int matrix[rows][cols] = { {1, 2, 3}, {4, 5, 6}, {7, 8, 9} };// 输出矩阵for(int i = 0; i < rows; ++i) {for(int j = 0; j < cols; ++j) {cout << matrix[i][j] << " ";}cout << endl;}return 0;
}
  1. 使用std::vector
#include <iostream>
#include <vector>
using namespace std;int main() {const int rows = 3;const int cols = 3;vector<vector<int>> matrix(rows, vector<int>(cols, 0));// 初始化矩阵int value = 1;for(int i = 0; i < rows; ++i) {for(int j = 0; j < cols; ++j) {matrix[i][j] = value++;}}// 输出矩阵for(const auto& row : matrix) {for(int elem : row) {cout << elem << " ";}cout << endl;}return 0;
}

我们可以看到,对于二维std::vector 的声明 已经长的很造孽,你可以创建一个辅助函数来简化二维vector的初始化:

#include <vector>std::vector<std::vector<int>> createMatrix(int rows, int cols, int initial_value = 0) {return std::vector<std::vector<int>>(rows, std::vector<int>(cols, initial_value));
}int main() {int rows = 3;int cols = 4;auto matrix = createMatrix(rows, cols);// Now matrix is a 3x4 matrix initialized with 0s
}

再看下三维vector的声明:

std::vector<std::vector<std::vector<int>>> vec3d(x, std::vector<std::vector<int>>(y, std::vector<int>(z, 0)));

更遭孽了,我们在深度学习的各种应用中,对于张量的计算,会经常用到矩阵,这样无疑有着巨大的代码量。但是我们可以用一些实用库来解决这一难题。

在深度学习中多种库对于矩阵的支持

在深度学习应用中,有几个流行的C++库支持矩阵和张量运算。以下是其中一些常用的库:

Eigen:Eigen是一个开源的C++模板库,提供了线性代数、矩阵运算和向量运算的功能。它可以作为深度学习库的基础,用于实现矩阵和张量的基本操作。

DLIB:DLIB是一个包含机器学习算法和工具的C++库,它包括了矩阵、线性代数和图像处理等方面的功能,可以用于深度学习模型的实现和训练。

ArrayFire:ArrayFire是一个高性能的并行计算库,提供了对多维数组(包括矩阵和张量)的快速运算功能,适用于深度学习中大规模数据的处理。

Armadillo:Armadillo是一个C++模板库,提供了高性能的线性代数运算和矩阵运算功能,可以用于深度学习模型的实现和优化。

opencv: OpenCV(Open Source Computer Vision Library)主要是用于计算机视觉领域的开源库,虽然它的主要目标是图像处理和计算机视觉任务,但也包含了一些基本的矩阵和张量运算功能。它提供了对多维数据结构(如矩阵)的支持,并且可以用于某些深度学习任务中的数据处理和预处理。

一些库的运用

Eigen是一个高性能的矩阵和线性代数库,在SLAM运用中,熟练使用Eigen库是基本需求,它提供了丰富的功能并且易于使用。
Eigen 是一个高性能的线性代数库,广泛应用于科学计算和工程领域。它具有以下特点:

高性能:Eigen 实现了多种优化技术,如矢量化、缓存友好算法等,能提供高效的矩阵运算。
简单易用:Eigen 提供了丰富的接口,并且使用起来非常直观。
广泛支持:支持各种矩阵和向量操作,包括基本的代数运算、解线性方程组、特征值分解等。
良好的文档:Eigen 有详细的文档和示例,便于学习和使用。

#include <iostream>
#include <Eigen/Dense>using namespace std;
using namespace Eigen;int main() {Matrix3f matrix; // 创建3x3的float类型矩阵// 初始化矩阵matrix << 1, 2, 3,4, 5, 6,7, 8, 9;cout << "Matrix:\n" << matrix << endl;// 转置矩阵Matrix3f transpose = matrix.transpose();cout << "Transpose:\n" << transpose << endl;// 矩阵乘法Matrix3f result = matrix * transpose;cout << "Matrix * Transpose:\n" << result << endl;return 0;
}

Armadillo
Armadillo是另一个高效的线性代数库,语法接近MATLAB。(这个我没用过)需要安装Armadillo库:

#include <iostream>
#include <armadillo>using namespace std;
using namespace arma;int main() {mat A = {{1, 2, 3},{4, 5, 6},{7, 8, 9}};cout << "Matrix A:\n" << A << endl;// 转置矩阵mat At = A.t();cout << "Transpose of A:\n" << At << endl;// 矩阵乘法mat B = A * At;cout << "A * Transpose of A:\n" << B << endl;return 0;
}

OpenCV 中,矩阵是通过 cv::Mat 类来表示的。

创建矩阵
你可以使用不同的构造函数来创建 cv::Mat 对象,例如:

通过指定行数、列数和数据类型来创建矩阵:

cv::Mat mat1(rows, cols, CV_8UC3);  // 8-bit 无符号整数,3通道颜色图像

通过传入已有的数据来创建矩阵:

float data[] = {1.2, 2.5, 3.7, 4.1};
cv::Mat mat2(2, 2, CV_32FC1, data);  // 32-bit 浮点数,单通道图像

通过复制已有的矩阵来创建新的矩阵:

cv::Mat mat3 = mat1.clone();

访问矩阵元素
你可以通过 at 方法或者 ptr 方法来访问矩阵的元素,例如:

float value = mat1.at<float>(i, j);  // 访问第 i 行、第 j 列的元素

或者:

for (int i = 0; i < mat2.rows; i++) {float* row_ptr = mat2.ptr<float>(i);  // 获取第 i 行的指针for (int j = 0; j < mat2.cols; j++) {float value = row_ptr[j];  // 访问第 i 行、第 j 列的元素}
}

矩阵操作
OpenCV 提供了丰富的矩阵操作函数,包括矩阵加法、减法、乘法、转置、逆矩阵计算等。例如,你可以使用 cv::add 函数来进行矩阵加法:

cv::Mat result;
cv::add(mat1, mat2, result);  // 将 mat1 和 mat2 相加,结果存储到 result 中

使用矩阵进行图像处理
由于 OpenCV 主要用于图像处理,因此 cv::Mat 类也经常用来表示图像。你可以通过 cv::imread 函数加载图像为 cv::Mat 对象,然后对图像进行各种操作,比如改变亮度、对比度、图像滤波、边缘检测等。

总之,OpenCV 中的 cv::Mat 类提供了灵活、高效的多维数组表示,适用于图像处理和其他计算机视觉应用。它不仅可以用于表示图像数据,还可以用于一般的矩阵运算和线性代数计算。

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mzph.cn/web/28810.shtml

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

jeecg快速启动(附带本地运行可用版本下载)

版本整理&#xff08;windows x64位&#xff09;&#xff1a; redis&#xff1a;3.0.504 MYSQL&#xff1a;5.7 Maven&#xff1a;3.9.4(setting文件可下载) Nodejs&#xff1a;v16.20.2&#xff08;建议不要安装默认路径下&#xff0c;如已安装在c盘&#xff0c;运行yarn报…

SAP 在过账的时候系统提示:被合并的公司 XXXX 和 ‘ ‘ 是不同的解决办法

最近用户反馈在STO的业务模式中交货单过账的时候&#xff0c;报错没有办法过账。查看了一下报错的信息提示&#xff1a;被合并的公司 和1300是不同的 如下图所示&#xff1a; 消息号是F5080 首先根据SAP的消息号找了一下NOTE&#xff0c;发现2091823有详细的说。 主要是财务…

准备好迎接3D世界的AI革新了吗:Direct3D,让3D创作触手可及

DreamTech 推出原生 3D-DiT 大模型 Direct3D 前言 3D-DiT大模型Direct3D 就目前的AI市场而言&#xff0c;将文本和图像转化为高质量的3D资产一直很难实现&#xff0c;主要目前缺乏一种能够捕捉复杂几何结构而且还能够扩展的3D的方法。但 DreamTech 发布了一种名为Direct3D的新型…

网络安全 DVWA通关指南 SQL Injection(SQL注入)

DVWA SQL Injection 文章目录 DVWA SQL InjectionLowMediumHighImpossible SQL注入漏洞基本原理 Web应用程序对用户输入的数据校验处理不严或者根本没有校验&#xff0c;致使用户可以拼接执行SQL命令。 可能导致数据泄露或数据破坏&#xff0c;缺乏可审计性&#xff0c;甚至导致…

小程序的 web-view 组件:实现点击跳转外部链接的高级技巧

在小程序开发中&#xff0c;web-view 组件不仅能够提供基本的网页嵌入功能&#xff0c;还可以通过一些高级技巧来增强用户体验和页面性能。本文将深入探讨如何利用 web-view 组件实现更高效、更安全的页面跳转至外部链接。 一、web-view 组件简介 web-view 是小程序中用于嵌入…

做恒指交易一定要有耐心

1、记住成为赢利的交易者是一个旅程&#xff0c;而非目的地。世界上并不存在只赢不输的交易者。试着每天交易的更好一些&#xff0c;从自己的进步中得到乐趣。聚精会神学习技术分析的技艺&#xff0c;提高自己的交易技巧&#xff0c;而不是仅仅把注意力放在自己交易输赢多少上。…

vite配置之获取.env.[mode]下的数据

需求 vite.config.ts获取配置文件下面的数据.vue,.ts,.tsxsrc文件夹下面获取配置文件下面的数据 一、src/* .vue,.ts,.tsx 文件夹下面使用环境变量 之前webpack或者用的vue-cli我们在获取配置文件数据的时候通过process.env&#xff0c;但是在vite里面不能通过这种方式 vit…

Redis作者长文总结LLMs, 能够取代99%的程序员

引言 这篇文章并不是对大型语言模型&#xff08;LLMs&#xff09;的全面回顾。很明显&#xff0c;2023年对人工智能而言是特别的一年&#xff0c;但再次强调这一点似乎毫无意义。相反&#xff0c;这篇文章旨在作为一个程序员个人的见证。自从ChatGPT问世&#xff0c;以及后来使…

保姆级pycharm远程连接linux服务器

1、登录服务器&#xff0c;创建账号。 一般都是管理员账户登录&#xff0c;创建自己的账号。如果不需要&#xff0c;可跳过这步。 打开MobaXterm&#xff0c;点击左上角Session创建会话。 再点击左上角SSH&#xff0c;分别输入服务器ip和账号&#xff0c;最后点ok&#xff0c;进…

有声读物管理平台Booksonic-Air

老苏最近在听评书&#xff0c;所以想找个软件来管理和收听&#xff0c;找了一圈&#xff0c;感觉 Booksonic-Air 可能能满足老苏的需求。 什么是 Booksonic-Air &#xff1f; Booksonic-Air 是一个用于流式传输有声读物的服务器&#xff0c;是原始 Booksonic 服务器的后继者。…

linux在文件夹中查找文件内容

linux在文件夹中查找文件内容 在Linux中,可以通过以下多个途径,在文件夹中查找文件内容: 1、使用grep命令: grep -r "要查找的内容" /path/to/folder-r参数表示递归地在文件夹及其子文件夹中搜索。/path/to/folder是要搜索的文件夹路径。2、使用ack命令 ack …

通过Vue3+高德地图的JS API实现市区地图渲染

效果图: 核心代码: <script setup>import { onMounted, onUnmounted } from vue;import AMapLoader from @amap/amap-jsapi-loader;import { message } from ant-design-vue;import school from @/assets/icons/school.svg;import enterprise from @/assets/icons/ent…

【Prometheus】自动化效率脚本

定义ip列表文件 cat ip_list.tx ##按照这个格式定义多个ip 192.168.1.1 192.168.1.2 脚本1 &#xff1a;一键telnet ip列表的9100端口可达性 # cat telnet.sh #!/bin/bash# Set the file name filename"ip_list.txt"# Read the file content into a variable ip_l…

英特尔 “AI” 科通:英特尔AI大模型应用前瞻

亲爱的科技探险家、前沿探索者、对未来深具好奇心的您&#xff0c; 身处人工智能引领的时代&#xff0c;我们目睹着行业的革命性变革。技术的创新不仅改变着我们的日常&#xff0c;更重新定义着我们对未来的期许。今天&#xff0c;怀着无限激情和期待&#xff0c;我们邀请您参…

SHH远程管理

4.1SHH远程管理 SSH是一种安全通道协议&#xff0c;主要用来实现字符界面的远程登录&#xff0c;远程复制等功能。 4.1.1配置OpenSSH服务器 在 CentOS 7.3 系统中&#xff0c;OpenSSH 服务器由 openssh、openssh-server 等软件包提供(默认已安装)&#xff0c;并已将 sshd 添…

Java多线程设计模式之保护性暂挂模式

模式简介 多线程编程中&#xff0c;为了提高并发性&#xff0c;往往将一个任务分解为不同的部分。将其交由不同的线程来执行。这些线程间相互协作时&#xff0c;仍然可能会出现一个线程等待另一个线程完成一定的操作&#xff0c;其自身才能继续运行的情形。 保护性暂挂模式&a…

Circle FFT in the Plonky3

传统的STARK系统需要在域中具有平滑阶数的循环群。如此&#xff0c;可以通过采用快速傅里叶变换&#xff08;FFT&#xff09;算法高效的计算多项式的插值点&#xff0c;并在相邻行中加入约束。对于具有阶数为 n n n 单位根的有限域 F p \mathbb{F}_p Fp​&#xff0c;对于很多…

【代码随想录算法训练营第四十天|卡码网46.携带研究材料,416.分割等和子集】

文章目录 卡码网46.携带研究材料二维dp数组一维dp数组&#xff08;滚动数组&#xff09; 416.分割等和子集 卡码网46.携带研究材料 这题是01背包问题。 二维dp数组 dp数组[i][j]前一位表示的是物品的种类&#xff0c;后一位表示的是背包的容量&#xff0c;在物体为i时&#…

Android Room数据库使用介绍

1.简介 Room是Google提供的Android架构组件之一&#xff0c;旨在简化数据库操作。它是SQLite的一个抽象层&#xff0c;提供了更易用和安全的API。 Room的总体架构: 2.Room数据库的基础概念 Entity Entity是Room中的数据表&#xff0c;每个Entity类对应一个SQLite表。 DAO …

研发团队的「技术债」如何进行量化管理?

我共事过的每个团队都会讨论技术债。有些团队知道如何管理它&#xff0c;也有些团队因此崩溃瘫痪&#xff0c;甚至有一家公司因为技术债务没有得到解决而宣告失败。 什么是技术债务&#xff1f; 「债务」这个比喻非常恰当。最早提出「技术债务 Technical Debt」比喻的工程师 W…