当前位置: 首页 > article >正文

别再傻傻用二维数组存大矩阵了!手把手教你用C++实现稀疏矩阵的三元组压缩(附完整代码)

稀疏矩阵高效存储实战从三元组压缩到十字链表的C实现当你在处理一个10000×10000的矩阵却发现其中99%的元素都是零时传统的二维数组存储方式就像用集装箱运输几颗散落的珍珠——浪费了巨大的空间和运输成本。这种稀疏场景在科学计算、图像处理和机器学习中比比皆是而聪明的开发者早已掌握了一套高效的存储方案。1. 为什么我们需要稀疏矩阵压缩想象一下城市间的航班网络全国有300个机场但每天实际运行的直飞航线可能只有3000条。如果用300×300的矩阵表示共9万个数据位其中87,000个位置都是零。这不仅浪费内存更会拖慢遍历和计算速度。传统二维数组的三大痛点内存占用与矩阵尺寸成正比而非实际数据量大量零值参与无效计算消耗CPU资源遍历效率低下特别是进行矩阵转置等操作时实测对比存储1000×1000矩阵含1%非零元素时二维数组占用3.8MB内存而三元组压缩仅需24KB内存节省达94%。2. 三元组顺序表入门级压缩方案三元组(Triple)是最直观的压缩方式每个非零元素用(行,列,值)表示。在C中我们可以这样定义数据结构struct Triple { int row; // 行索引从1开始 int col; // 列索引 double val; // 元素值 }; class SparseMatrix { private: int rows; // 总行数 int cols; // 总列数 int nonZeros; // 非零元素计数 vectorTriple data; // 三元组数组 };2.1 关键操作实现矩阵转置的优化算法 传统转置需要遍历原矩阵的每一列时间复杂度为O(cols×nonZeros)。我们可以通过预计算每列的非零数来优化void transpose() { vectorint colCount(cols 1, 0); vectorint startPos(cols 1); // 统计每列非零元素数 for (const auto item : data) { colCount[item.col]; } // 计算转置后每列的起始位置 startPos[1] 1; for (int i 2; i cols; i) { startPos[i] startPos[i-1] colCount[i-1]; } // 执行转置 vectorTriple newData(data.size()); for (const auto item : data) { int newPos startPos[item.col]; newData[newPos] {item.col, item.row, item.val}; } swap(rows, cols); data move(newData); }矩阵相加的边界处理 当两个矩阵维度不匹配时直接返回错误否则按行优先顺序合并bool add(const SparseMatrix other) { if (rows ! other.rows || cols ! other.cols) { cerr 维度不匹配无法相加 endl; return false; } vectorTriple result; int i 0, j 0; while (i nonZeros j other.nonZeros) { if (data[i].row other.data[j].row || (data[i].row other.data[j].row data[i].col other.data[j].col)) { result.push_back(data[i]); } else if (data[i].row other.data[j].row || (data[i].row other.data[j].row data[i].col other.data[j].col)) { result.push_back(other.data[j]); } else { double sum data[i].val other.data[j].val; if (sum ! 0) { result.push_back({data[i].row, data[i].col, sum}); } i; j; } } // 处理剩余元素 while (i nonZeros) result.push_back(data[i]); while (j other.nonZeros) result.push_back(other.data[j]); data move(result); nonZeros data.size(); return true; }3. 十字链表动态操作的进阶选择当矩阵需要频繁插入/删除非零元素时三元组顺序表的数组结构会因数据移动导致性能下降。十字链表(Orthogonal List)通过链表结构解决了这个问题。3.1 数据结构设计struct OLNode { int row, col; double val; OLNode* right; // 同行下一个非零元素 OLNode* down; // 同列下一个非零元素 }; class CrossListMatrix { private: int rows, cols; vectorOLNode* rowHeads; // 行头指针数组 vectorOLNode* colHeads; // 列头指针数组 };插入操作的实现技巧void insert(int r, int c, double v) { OLNode* newNode new OLNode{r, c, v, nullptr, nullptr}; // 处理行链表插入 if (!rowHeads[r] || rowHeads[r]-col c) { newNode-right rowHeads[r]; rowHeads[r] newNode; } else { OLNode* curr rowHeads[r]; while (curr-right curr-right-col c) { curr curr-right; } newNode-right curr-right; curr-right newNode; } // 处理列链表插入逻辑同上 if (!colHeads[c] || colHeads[c]-row r) { newNode-down colHeads[c]; colHeads[c] newNode; } else { OLNode* curr colHeads[c]; while (curr-down curr-down-row r) { curr curr-down; } newNode-down curr-down; curr-down newNode; } }4. 性能对比与选型指南存储方式内存占用随机访问顺序访问插入/删除适用场景二维数组O(mn)O(1)O(mn)O(1)密集矩阵三元组顺序表O(t)O(t)O(t)O(t)静态矩阵只读操作十字链表O(t)O(t)O(t)O(1)动态矩阵频繁修改选型建议当矩阵构建后不再修改时选择三元组顺序表需要频繁增删非零元素时使用十字链表对转置性能要求极高时考虑CSR/CSC格式进阶存储方案5. 实战中的性能陷阱与优化常见坑点未对三元组按行列排序导致操作性能退化忘记更新非零元素计数器(nonZeros)矩阵相乘时未利用稀疏特性退化为O(n³)复杂度高级优化技巧// 利用SIMD指令加速稀疏矩阵-向量乘法 void spmv(const vectordouble x, vectordouble y) { for (const auto item : data) { y[item.row] item.val * x[item.col]; } } // 分块存储提升缓存命中率 struct Block { int startRow, startCol; vectorTriple elements; }; vectorBlock blockedStorage;在图像处理项目中将256×256的稀疏DCT变换矩阵从二维数组改为三元组存储后内存占用从256KB降至3.2KB同时矩阵乘法速度提升了8倍——这正是稀疏存储的魅力所在。

相关文章:

别再傻傻用二维数组存大矩阵了!手把手教你用C++实现稀疏矩阵的三元组压缩(附完整代码)

稀疏矩阵高效存储实战:从三元组压缩到十字链表的C实现 当你在处理一个1000010000的矩阵,却发现其中99%的元素都是零时,传统的二维数组存储方式就像用集装箱运输几颗散落的珍珠——浪费了巨大的空间和运输成本。这种"稀疏"场景在科学…...

深入解析WIFI中EAP-TLS认证流程与安全机制

1. EAP-TLS认证:WIFI安全连接的基石 每次我们用手机连接公司或学校的WIFI时,系统总会弹出一个证书确认的窗口,这就是EAP-TLS在发挥作用。作为目前最安全的WIFI认证协议之一,它就像网络世界的"护照查验系统",…...

软电话通话30秒自动挂断?一文讲透FreeSWITCH通话超时问题

当你满怀期待地搭建好FreeSWITCH,用两个软电话成功呼叫,却发现通话总是在30秒左右莫名其妙地中断——别急,这是SIP新手最常遇到的“经典Bug”。本文将为你抽丝剥茧,彻底解决这个问题,并附带其他可能引发通话异常中断的…...

机械臂+点云相机实战:手眼标定全流程避坑指南(附PCL库代码)

机械臂与点云相机手眼标定实战:从原理到代码的完整避坑指南 在工业自动化与机器人应用领域,机械臂与3D视觉系统的协同作业已成为提升生产灵活性和智能化的关键技术。其中,手眼标定作为连接机械臂运动学与视觉感知的桥梁,其精度直接…...

Vitis自定义IP编译报错?手把手教你修复Makefile路径问题(附完整代码)

Vitis自定义IP编译报错?手把手教你修复Makefile路径问题(附完整代码) 最近在Vitis中导入包含自定义IP的XSA文件时,不少开发者遇到了令人头疼的编译错误——"xxx.h: No such file or directory"。这个看似简单的报错背后…...

java 短信验证码接口开发面向接口编程实现

在Java企业级后端开发中,短信验证码是用户登录、注册、密码重置的核心身份验证方案,java短信验证码接口的规范化开发直接决定系统的扩展性与维护性。传统硬编码开发模式存在耦合度高、服务商切换困难等问题,本文基于面向接口编程思想&#xf…...

Matlab 2024b 新变化:手把手教你搞定TI C2000代码生成环境(含CCS避坑指南)

Matlab 2024b与TI C2000代码生成环境配置全指南:从版本差异到实战避坑 如果你是一位长期使用Matlab进行TI C2000系列芯片开发的嵌入式工程师,升级到2024b版本后可能会发现:熟悉的配置界面不见了,命令行里输入的命令也不一样了。这…...

2026 机器人行业发展前景与 AI 获客方案深度解析

引言:机器人行业的爆发式增长与获客挑战2026 年 3 月,全球机器人行业正处于爆发前夜。数据显示,2026 年全球机器人市场规模预计将达到 4000 亿元,较 2025 年增长 25%(数据来自网络)。随着具身智能技术的加速…...

保姆级教程:在NUC12Pro上配置Ego_planner无人机自主飞行系统(含D435i与Pixhawk 6C)

在NUC12Pro上构建Ego_planner无人机自主飞行系统的全流程指南 当硬件堆满工作台时,最令人兴奋的莫过于将它们组装成一个能自主思考的飞行系统。本文将带您完成从零搭建基于NUC12Pro、D435i深度相机和Pixhawk 6C飞控的完整解决方案,重点解决那些官方文档从…...

隔离变送器VS普通变送器:为什么你的PLC信号总受干扰?(实测XYS-5531抗干扰性能)

隔离变送器VS普通变送器:为什么你的PLC信号总受干扰?(实测XYS-5531抗干扰性能) 在工业自动化现场,信号干扰就像潜伏的"隐形杀手"——它不会直接摧毁设备,却能让控制系统频繁误动作、数据采集失真…...

超实用!学生党第一把吉他怎么选?9款“低弦距神器”深度测评与避坑指南!

大家好,我是深耕音乐教育与乐器选购多年的好物推荐官,常年和学生党打交道,最常被问到的问题就是:“预算有限,怎么选到好弹又耐用的吉他?” 其实对学生而言,第一把吉他无需追求高端奢华&#xff…...

从Sigmoid函数到脉冲频率:步进电机S型加减速的数学建模与C/C++实现

1. 为什么步进电机需要S型加减速 我第一次接触步进电机控制时,以为只要给脉冲信号就能让电机转起来。结果在实际项目中,电机要么启动时丢步,要么停止时过冲,把机械结构撞得砰砰响。后来才知道,步进电机和普通直流电机不…...

Spring Boot 集成云快充协议:充电桩接入平台完整Demo

云快充协议云快充1.5协议云快充1.6云快充协议开源代码云快充底层协议云快充桩直连桩直连协议充电桩协议云快充源码介绍云快充协议云快充1.5协议云快充1.6云快充协议开源代码云快充底层协议云快充桩直连桩直连协议充电桩协议云快充源码软件架构1、提供云快充底层桩直连协议&…...

智能高效的离线OCR解决方案:Umi-OCR从基础到进阶的全方位应用指南

智能高效的离线OCR解决方案:Umi-OCR从基础到进阶的全方位应用指南 【免费下载链接】Umi-OCR Umi-OCR: 这是一个免费、开源、可批量处理的离线OCR软件,适用于Windows系统,支持截图OCR、批量OCR、二维码识别等功能。 项目地址: https://gitco…...

【BoClaw教程03】BoClaw实战:打工人常用技能

博云BoClaw官方教程系列(三)本教程聚焦打工人日常办公高频需求,详细讲解 BoClaw 在桌面整理、文档检索、PPT 制作、简历筛选、销售报表处理五大场景的实操方法、操作要点及避坑技巧,助力高效提升办公效率。1.桌面整理:…...

从‘画图’到‘造芯’:模拟版图工程师必须懂的CMOS工艺那些事儿

从‘画图’到‘造芯’:模拟版图工程师必须懂的CMOS工艺那些事儿 当你第一次打开PDK文档,面对密密麻麻的设计规则表格时,是否感觉像在解读天书?作为模拟版图工程师,我们每天都在与纳米级的几何图形打交道,但…...

自然滚动的终结:Scroll Reverser如何重构输入设备交互逻辑

自然滚动的终结:Scroll Reverser如何重构输入设备交互逻辑 【免费下载链接】Scroll-Reverser Per-device scrolling prefs on macOS. 项目地址: https://gitcode.com/gh_mirrors/sc/Scroll-Reverser 在追求无缝人机交互的今天,macOS系统中输入设备…...

Ubuntu 22.04 换源+Docker安装+镜像加速

Ubuntu 22.04 换源Docker安装镜像加速 前言 本文针对 Ubuntu 22.04 LTS 系统,先更换国内镜像源提升下载速度,再完成 Docker 引擎与 Compose 插件安装,最后配置 Docker 国内镜像加速,全程无报错、可直接复制执行,适配 V…...

QMCDecode:解锁QQ音乐加密文件的macOS终极解决方案

QMCDecode:解锁QQ音乐加密文件的macOS终极解决方案 【免费下载链接】QMCDecode QQ音乐QMC格式转换为普通格式(qmcflac转flac,qmc0,qmc3转mp3, mflac,mflac0等转flac),仅支持macOS,可自动识别到QQ音乐下载目录,默认转换…...

计算机毕业设计springboot校园外卖系统 基于Spring Boot的高校餐饮配送服务平台 Spring Boot框架下的校园在线订餐与配送管理系统

计算机毕业设计springboot校园外卖系统n322b9 (配套有源码 程序 mysql数据库 论文) 本套源码可以在文本联xi,先看具体系统功能演示视频领取,可分享源码参考。随着互联网技术的日益成熟和普及,网络已经深度融入人们的日常生活&…...

《Cancer Discov》(IF: 33.3)|新型空间蛋白组和空间转录组整合流程解析肿瘤免疫微环境

空间转录组学和空间蛋白组学能分别在原位解析基因表达和蛋白功能状态。然而,它们各有自己独特的应用场景,例如空间转录组覆盖广但预测功能不直接,而空间蛋白组功能信号直接,靶向性高,能提供更多的有效生物学信息。如果…...

5分钟掌握精灵图智能切割:Pixelorama扩展让资源提取效率倍增

5分钟掌握精灵图智能切割:Pixelorama扩展让资源提取效率倍增 【免费下载链接】Pixelorama A free & open-source 2D sprite editor, made with the Godot Engine! Available on Windows, Linux, macOS and the Web! 项目地址: https://gitcode.com/gh_mirrors…...

douyin-downloader:智能化解构无水印视频批量采集的技术方案

douyin-downloader:智能化解构无水印视频批量采集的技术方案 【免费下载链接】douyin-downloader 项目地址: https://gitcode.com/GitHub_Trending/do/douyin-downloader 在数字内容爆炸的时代,如何高效获取高质量视频素材成为内容创作者、研究者…...

使用pycharm调试后端项目

本文主要解决终端工具与charm环境隔离问题,让终端虚拟环境与pycharm进行关联,简化pycharm的操作第一步 安装 UV 并创建虚拟环境(uv工具安装步骤已经跳过,不知道怎么安装的找AI问)确保系统中已安装 UV 工具。若需特定 P…...

Claude Code 工程化实战:从工具使用者到 Agent 构建者的进阶之路

Claude Code 工程化实战:从工具使用者到 Agent 构建者的进阶之路 声明: 📝 作者:甜城瑞庄的核桃(ZMJ) 原创学习笔记,欢迎分享,但请保留作者信息及原文链接哦~ 摘要&#…...

告别Joplin!用MarkDownload+Obsidian打造你的网页剪藏工作流(附完整配置JSON)

从Joplin到Obsidian:用MarkDownload构建高效网页剪藏系统 每次在网上冲浪时遇到值得保存的内容,你是否也经历过这样的困境?收藏夹里堆满了再也找不到的链接,或是剪藏工具中杂乱无章的片段。作为一个长期依赖Joplin进行知识管理的用…...

STM32F1XX 的 CAN 的 波特率配置

参考文档: CAN总线波特率的设定——以STM32F103为例 - 知乎 42. CAN—通讯实验 — [野火]STM32库开发实战指南——基于野火霸道开发板 文档 基本知识 (SMP 采样率) STM32F1系列开发板设置的系统时钟大小 SYSCLK(系统时钟&…...

Claude Remote Control 技术详解:跨设备无缝协作的远程会话控制方案

Claude Remote Control 技术详解:跨设备无缝协作的远程会话控制方案 声明: 📝 作者:甜城瑞庄的核桃(ZMJ) 原创学习笔记,欢迎分享,但请保留作者信息及原文链接哦~ 引言 在现代软件开发场景中,开发者经常需要在多个设备间切换工作环境。Claude Code 推出的 Remote Con…...

在曹妃甸哪里可以吃到当天现捕上来的野生海鲜?

在曹妃甸,想要吃到当天现捕上来的野生海鲜,高尚堡老刘海鲜绝对是个绝佳的选择。2006 年,一群世代靠海吃海的渔民,在渤海湾码头开起了这家“老刘海鲜饭店”。起初他们只是想把自家渔船捕捞的野生海鲜,用最朴素的做法端给…...

Llama-3.2V-11B-cot部署详解:自动修复视觉权重加载致命Bug全过程

Llama-3.2V-11B-cot部署详解:自动修复视觉权重加载致命Bug全过程 1. 项目概述 Llama-3.2V-11B-cot是基于Meta Llama-3.2V-11B-cot多模态大模型开发的高性能视觉推理工具,专为双卡RTX 4090环境深度优化。本工具通过自动修复视觉权重加载等核心Bug&#…...