news 2026/5/1 11:08:45

C++共享内存小白入门指南

作者头像

张小明

前端开发工程师

1.2k 24
文章封面图
C++共享内存小白入门指南

什么是共享内存?

想象一下,你和你的室友共用一个冰箱。你们都可以往里面放东西,也可以从里面拿东西,这就是共享内存的基本概念!在C++中,共享内存是一种让不同进程(可以理解为不同的程序)能够访问同一块内存区域的技术。

为什么要使用共享内存?

  1. 高效通信:进程间通信最快的方式之一
  2. 数据共享:多个程序可以访问相同数据
  3. 减少复制:不需要在不同进程间复制大量数据

基础知识准备

在深入之前,你需要知道:

  • 进程:正在运行的程序实例
  • 内存:程序存储数据的地方
  • 系统调用:操作系统提供的功能接口

共享内存使用步骤(Linux/Unix系统)

第一步:创建共享内存

#include<sys/ipc.h>#include<sys/shm.h>#include<iostream>intmain(){// 生成一个唯一的keykey_t key=ftok("shmfile",65);// 创建共享内存段,1024字节大小// IPC_CREAT表示创建,0666是权限(可读可写)intshmid=shmget(key,1024,IPC_CREAT|0666);if(shmid<0){std::cerr<<"创建共享内存失败"<<std::endl;return1;}std::cout<<"共享内存创建成功,ID: "<<shmid<<std::endl;return0;}

第二步:附加到共享内存

#include<sys/ipc.h>#include<sys/shm.h>#include<iostream>#include<cstring>intmain(){key_t key=ftok("shmfile",65);intshmid=shmget(key,1024,0666);// 附加到共享内存char*shared_memory=(char*)shmat(shmid,nullptr,0);if(shared_memory==(char*)-1){std::cerr<<"附加到共享内存失败"<<std::endl;return1;}// 写入数据到共享内存std::strcpy(shared_memory,"你好,共享内存!");std::cout<<"数据已写入共享内存"<<std::endl;// 分离共享内存(但不删除)shmdt(shared_memory);return0;}

第三步:读取共享内存数据

#include<sys/ipc.h>#include<sys/shm.h>#include<iostream>intmain(){key_t key=ftok("shmfile",65);intshmid=shmget(key,1024,0666);// 附加到共享内存char*shared_memory=(char*)shmat(shmid,nullptr,0);std::cout<<"从共享内存读取: "<<shared_memory<<std::endl;// 分离共享内存shmdt(shared_memory);return0;}

第四步:删除共享内存

#include<sys/ipc.h>#include<sys/shm.h>#include<iostream>intmain(){key_t key=ftok("shmfile",65);intshmid=shmget(key,1024,0666);// 删除共享内存段shmctl(shmid,IPC_RMID,nullptr);std::cout<<"共享内存已删除"<<std::endl;return0;}

完整示例:进程间通信

写入进程(writer.cpp)

#include<sys/ipc.h>#include<sys/shm.h>#include<iostream>#include<cstring>#include<unistd.h>intmain(){// 生成keykey_t key=ftok("shmfile",65);// 创建共享内存(1KB大小)intshmid=shmget(key,1024,IPC_CREAT|0666);// 附加到共享内存char*str=(char*)shmat(shmid,nullptr,0);std::cout<<"写入进程启动,等待输入..."<<std::endl;// 连续写入数据for(inti=1;i<=5;i++){sprintf(str,"消息 %d",i);std::cout<<"写入: "<<str<<std::endl;sleep(2);// 等待2秒}// 写入结束标志strcpy(str,"结束");// 分离共享内存shmdt(str);return0;}

读取进程(reader.cpp)

#include<sys/ipc.h>#include<sys/shm.h>#include<iostream>#include<cstring>#include<unistd.h>intmain(){// 生成相同的keykey_t key=ftok("shmfile",65);// 获取共享内存intshmid=shmget(key,1024,0666);// 附加到共享内存char*str=(char*)shmat(shmid,nullptr,0);std::cout<<"读取进程启动,等待数据..."<<std::endl;// 持续读取数据while(true){std::cout<<"读取: "<<str<<std::endl;// 检查是否收到结束标志if(strcmp(str,"结束")==0){break;}sleep(1);// 每秒检查一次}// 分离共享内存shmdt(str);// 删除共享内存段shmctl(shmid,IPC_RMID,nullptr);std::cout<<"共享内存已清理"<<std::endl;return0;}

编译和运行

# 编译写入进程g++ writer.cpp -o writer# 编译读取进程g++ reader.cpp -o reader# 打开两个终端,先运行写入进程./writer# 在另一个终端运行读取进程./reader

Windows下的共享内存(简单示例)

#include<windows.h>#include<iostream>#include<string>intmain(){// 创建共享内存HANDLE hMapFile=CreateFileMapping(INVALID_HANDLE_VALUE,// 使用系统页面文件nullptr,// 默认安全属性PAGE_READWRITE,// 可读可写0,// 高位文件大小256,// 低位文件大小(256字节)L"MySharedMemory");// 共享内存名称// 映射到进程地址空间char*pBuf=(char*)MapViewOfFile(hMapFile,// 共享内存句柄FILE_MAP_ALL_ACCESS,// 可读可写访问0,0,256);// 使用共享内存strcpy(pBuf,"Windows共享内存示例");std::cout<<"写入: "<<pBuf<<std::endl;// 清理UnmapViewOfFile(pBuf);CloseHandle(hMapFile);return0;}

注意事项和最佳实践

  1. 同步问题:多个进程同时访问时需要同步机制(如信号量)
  2. 内存泄漏:确保正确释放共享内存
  3. 安全性:共享内存对所有有权限的进程可见
  4. 大小限制:系统对共享内存大小有限制

常见问题解答

Q: 共享内存和普通内存有什么区别?
A: 共享内存可以被多个进程访问,普通内存只能被创建它的进程访问。

Q: 进程退出后共享内存还在吗?
A: 除非显式删除,否则共享内存会一直存在。

Q: 如何防止数据冲突?
A: 使用同步机制,如互斥锁、信号量等。

Q: 共享内存大小有限制吗?
A: 有,取决于系统配置,通常可以通过系统命令查看和调整。

学习建议

  1. 从简单的示例开始,先理解基本概念
  2. 实践编写两个进程通信的程序
  3. 学习同步机制,处理并发访问
  4. 查阅系统文档,了解具体限制和特性

记住,共享内存是强大的工具,但需要谨慎使用。确保你理解了同步和清理的重要性,避免内存泄漏和数据损坏。祝你学习顺利!

版权声明: 本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若内容造成侵权/违法违规/事实不符,请联系邮箱:809451989@qq.com进行投诉反馈,一经查实,立即删除!
网站建设 2026/5/1 9:58:48

仓库 Reel ID

“仓库 Reel ID” 是在仓储管理、电子元器件、SMT&#xff08;表面贴装技术&#xff09;等行业中常见的一个术语&#xff0c;尤其在 高价值、小体积、卷带包装物料的精细化管理场景 中广泛使用。&#x1f4cc; 一、“Reel ID” 是什么&#xff1f;Reel ID&#xff08;卷盘编号&…

作者头像 李华
网站建设 2026/4/28 9:09:45

从零搭建智能体:用数眼智能构建 AI 智能体 Agent 实战

一、为什么选择数眼智能构建 AI Agent&#xff1f;—— 解决联网型 Agent 的核心痛点 传统 AI 模型&#xff08;如 ChatGPT&#xff09;仅能被动生成回答&#xff0c;普通 AI Agent 虽能调用工具&#xff0c;但在实时联网场景中常踩坑&#xff1a;信息过期&#xff08;用半年前…

作者头像 李华
网站建设 2026/4/23 14:03:59

积分理财骗局终落幕 监管导向解读为新消费划清合规红线

新消费浪潮下&#xff0c;“消费积分”本是提升用户粘性的良性工具&#xff0c;却被部分不法企业异化为圈钱利器。此前备受关注的“翰林金业”非法集资、传销案&#xff0c;便是新消费领域违规经营的典型缩影&#xff0c;其覆灭再次为行业敲响合规警钟。 “翰林金业”以“绿色消…

作者头像 李华
网站建设 2026/5/1 10:03:23

搭建禅道环境作为练习UI和接口自动化测试对象

1 目的 做UI和接口自动化练习时&#xff0c;有时候找不到合适的对象&#xff0c;我们可使用禅道来联系&#xff1b; 因为禅道有开源版&#xff0c;可以二次开发&#xff0c;并有详细的API手册&#xff1b; 本文的目的是整理并分享&#xff0c;使用禅道来作为测试对象的过程&a…

作者头像 李华
网站建设 2026/5/1 8:33:41

不属于五种算法就无需备案?关于算法备案的常见误区解析

在AI快速发展的今天&#xff0c;算法已成为互联网服务的核心驱动力。从个性化推荐到智能决策&#xff0c;算法深度嵌入我们的日常生活。然而&#xff0c;随着其广泛应用&#xff0c;算法带来的潜在风险——如“大数据杀熟”、算法歧视、信息茧房等问题——也引发了监管部门的高…

作者头像 李华