c#实现内存映射文件共享内存

2023-05-16

内存映射文件是利用虚拟内存把文件映射到进程的地址空间中去,在此之后进程操作文件,就像操作进程空间里的地址一样了,比如使用c语言的 memcpy等内存操作的函数。这种方法能够很好的应用在需要频繁处理一个文件或者是一个大文件的场合,这种方式处理IO效率比普通IO效率要高

共享内存是内存映射文件的一种特殊情况,内存映射的是一块内存,而非磁盘上的文件。共享内存的主语是进程(Process),操作系统默认会给每一 个进程分配一个内存空间,每一个进程只允许访问操作系统分配给它的哪一段内存,而不能访问其他进程的。而有时候需要在不同进程之间访问同一段内存,怎么办 呢?操作系统给出了创建访问共享内存的API,需要共享内存的进程可以通过这一组定义好的API来访问多个进程之间共有的内存,各个进程访问这一段内存就 像访问一个硬盘上的文件一样。而.Net 4.0中引入了System.IO. MemoryMappedFiles命名空间,这个命名空间的类对windows 共享内存相关API做了封装,使.Net程序员可以更方便的使用内存映射文件。

在C#中使用共享内存。以下App1的代码让用户输入一行文本到共享内存中;App2不停的刷新控制台,输出最新的共享内存内容;App3实现的功能和App2相同,但读取方法不同。


App1代码:
using System;
using System.Collections.Generic;android从资源文件中读取文件流显示
using System.Linq;
using System.Text;

using System.IO;

//引用内存映射文件命名空间
using System.IO.MemoryMappedFiles;

namespace App1
{
    class Program
    {
        static void Main(string[] args)
        {
            long capacity = 1<<10<<10;

            //创建或者打开共享内存
            using (var mmf = MemoryMappedFile.CreateOrOpen("testMmf", capacity, MemoryMappedFileAccess.ReadWrite))
            {
                //通过MemoryMappedFile的CreateViewAccssor方法获得共享内存的访问器
                var viewAccessor = mmf.CreateViewAccessor(0, capacity);
                //循环写入,使在这个进程中可以向共享内存中写入不同的字符串值
                while (true)
                {
                    Console.WriteLine("请输入一行要写入共享内存的文字:");

                    string input = Console.ReadLine();

                    //向共享内存开始位置写入字符串的长度
                    viewAccessor.Write(0, input.Length);

                    //向共享内存4位置写入字符
                    viewAccessor.WriteArray<char>(4, input.ToArray(), 0, input.Length);
                }

            }
            
        }
    }
}


App2代码:
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading;

//引用使用内存映射文件需要的命名空间
using System.IO.MemoryMappedFiles;

namespace App2
{
    class Program
    {
        static void Main(string[] args)
        {
              long capacity = 1<<10<<10;

              using (var mmf = MemoryMappedFile.OpenExisting("testMmf"))
              {
                  MemoryMappedViewAccessor viewAccessor = mmf.CreateViewAccessor(0, capacity);

                  //循环刷新共享内存字符串的值
                  while (true)
                  {
                      //读取字符长度
                      int strLength = viewAccessor.ReadInt32(0);                      
                      char[] charsInMMf = new char[strLength];
                      //读取字符
                      viewAccessor.ReadArray<char>(4, charsInMMf, 0, strLength);
                      Console.Clear();
                      Console.Write(charsInMMf);
                      Console.Write("\r");
                      Thread.Sleep(200);
                  }
              }
        }
    }
}

App3代码:
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;

using System.IO.MemoryMappedFiles;
using System.IO;

namespace App3
{
    class Program
    {
        static void Main(string[] args)
        {
            long capacity = 1 << 10 << 10;
            //打开共享内存
            using (var mmf = MemoryMappedFile.OpenExisting("testMmf"))
            {
                //使用CreateViewStream方法返回stream实例
                using (var mmViewStream = mmf.CreateViewStream(0, capacity))
                {
                    //这里要制定Unicode编码否则会出问题
                    using (BinaryReader rdr = new BinaryReader(mmViewStream,Encoding.Unicode))
                    {
                        while (true)
                        {
                            mmViewStream.Seek(0, SeekOrigin.Begin);

                            int length = rdr.ReadInt32();

                            char[] chars = rdr.ReadChars(length);

                            Console.Write(chars);
                            Console.Write("\r");

                            System.Threading.Thread.Sleep(200);
                            Console.Clear();
                        }
                    }
                }
            }
        }
    }
}
在读数据时用了2种方法。

因为在之前很少会用到进程之间的通信,所以此方法只是想初步的认识下。此程序写的过于简陋,有很多东西都没有去判断。比如说是怎么创建了一个共享内存怎么取删除它等等。。。

希望我与此篇博文的作者共勉吧。




本文内容由网友自发贡献,版权归原作者所有,本站不承担相应法律责任。如您发现有涉嫌抄袭侵权的内容,请联系:hwhale#tublm.com(使用前将#替换为@)

c#实现内存映射文件共享内存 的相关文章

  • 从 C51+uCos-II 近距离了解操作系统任务切换原理

    前言 从 C51 43 uCos II 简单介绍下任务切换的原理 方便大家更形象的理解多任务怎么切换 为后续写 x86 43 Linux 任务切换做铺垫练手吧 参考资料如下 xff1a uCos II 源码 单片机原理与应用及 C51 编程
  • Keil+Simulink生成Xcp标定协议A2L文件

    Keil 43 Simulink生成Xcp标定协议A2L文件 由于最近要为ECU移植XCP协议 xff0c 所以记录一下 xff0c 我使用的MCU为NXP S32K144 IDE选用MDK 官方IDE S32DS无代码联想功能 xff0c
  • 记录一下关于MPC5744P CAN总线学习

    记录一下关于MPC5744P CAN总线学习 主要是针对开发出BUSOFF管理 xff0c NXP感觉都是一个套路 xff0c 无论powerpc xff0c 还是arm m status t span class token functi
  • 通过.map文件填写XCP标定需要的A2L文件

    首先你得有一个模板 xff0c 通过python脚本打开编译后的 map文件自动填写到A2L文件对应位置 xff0c 目前只实现了填写Mesurement 区域 xff0c 但是这个填写主要是更新变量名和对应的ECU ADRRESS 因为
  • Autosar Xcp移植

    前言 xff1a 可能有兄弟胸中有点疑问 Vector ETAS等软件包都有XCP xff0c 你移植个吊 xff0c 但是我的MICORSAR BSW中没发现XCP静态代码 xff0c 倒是在CFG中发现了XCP配置选项 xff0c 难道
  • Tricore学习-芯片启动流程

    第一次接触Tricore 学习下从芯片上电到运行到main函数的过程 xff0c 本文以TC36X为例 xff0c 具体可参考英飞凌官方的Infineon AURIX TC3xx Part1 UserManual v02 00 EN 首先T
  • ETAS-AUTOSAR学习-0.1Task配置思考

    span class token function TASK span span class token punctuation span OsTask BSW span class token punctuation span span
  • AurixDevStudio集成MCAL

    这是Tricore MCAL安装路径 打开ADS新建一个AURIX Project 我手上的是龙邱的TC377最小系统 就这样选 理解下第一个选项 新建好的基础工程是这个样子 删除掉Library文件夹 因为我们这里要使用的MCAL而不是i
  • git 使用命令创建新分支

    如何使用Git 命令创建一个新分支 使用场景 xff1a 本文主要详细介绍了如何使用git命令基于一个项目的master分支创建一个新的git分支 xff0c 并且推向远程仓库 xff0c 使其他开发人员能够功能使用该分支进行开发 操作步骤
  • go web gin框架实战1

    文章目录 go web gin框架实战1 参考资料2 demo3 demo运行4 demo解析 go web gin框架实战 1 参考资料 gin框架官方文档 链接 2 demo span class token keyword packa
  • Hadoop之MapReduce

    摘要 xff1a MapReduce是Hadoop的又一核心模块 xff0c 从MapReduce是什么 xff0c MapReduce能做什么以及MapReduce的工作机制三方面认识MapReduce 关键词 xff1a Hadoop
  • Linux常用命令

    摘要 xff1a 采用命令行模式操控Linux系统非常重要 本文总结Linux常用的命令 xff0c 包括命令的含义 xff0c 命令的用法以及命令的拓展 关键词 xff1a 命令行模式 Linux常用命令 给Linux系统下达命令 xff
  • Hadoop之HDFS文件操作

    摘要 xff1a Hadoop之HDFS文件操作常有两种方式 xff0c 命令行方式和JavaAPI方式 本文介绍如何利用这两种方式对HDFS文件进行操作 关键词 xff1a HDFS文件 命令行 Java API HDFS是一种分布式文件
  • R实战读书笔记四

    第三章 图形入门 本章概要 1 创建和保存图形 2 定义符号 线 颜色和坐标轴 3 文本标注 4 掌控图形维数 5 多幅图合在一起 本章所介绍内容概括如下 一图胜千字 xff0c 人们从视觉层更易获取和理解信息 图形工作 R具有非常强大的绘
  • R语言——数据分析的一把利剑

    R语言 xff0c 我把它称之为数据分析的一把利剑 为什么这么说呢 xff1f 先让我们看一下 xff0c 什么是数据分析 xff1f 所谓数据分析 xff0c 就是以商业目的为驱动 xff0c 所开展的获取数据 处理数据 分析数据 展示数
  • 【爱上Linux】第一课 Linux概述

    学习应该是快乐的事情 快乐的东西应该要分享开来 xff0c 人人都快乐 xff01 爱上Linux 第一课 Linux概述 在本课中 xff0c 和朋友们一起来思考这些问题 问题一 xff1a 谈Linux学习 xff1f 从四个方面来看
  • 链表的创建与遍历

    链表 xff0c 简而言之 xff0c 就是基于链式储存结构下的线性表 链表包括单向链表 双向链表以及循环链表 链表是一种很常用的数据结构 xff0c 其定义如下 xff1a 单向链表的定义 定义说明 xff1a 包括数据域和指针域 typ
  • Java异常机制

    Java异常 xff08 Exception xff09 又称例外 xff0c 是一种运行时错误 Java异常机制就是对于Java异常的处理方法 xff0c 使用Java异常机制能提升程序的容错性 xff0c 从而使程序更加健壮与安全 ja
  • Java序列化与反序列化

    Java序列化与反序列化是什么 xff1f 为什么需要序列化与反序列化 xff1f 如何实现Java序列化与反序列化 xff1f 本文围绕这些问题进行了探讨 1 Java序列化与反序列化 Java序列化是指把Java对象转换为字节序列的过程
  • Java语言中几个常用的包

    Java采用包结构来组织和管理类和接口文件 本文介绍Java语言类库中几个常用的包 xff0c 因为这几个包在软件开发与应用中经常需要用到 xff0c 其中有些包是必要的 若是离开它 xff0c 还真不能做事情了 第一个包 xff1a ja

随机推荐

  • 计算机网络

    Cname和A记录 CNAME和A记录 A记录 Address记录 xff0c 代表指向关系 www xx com 1 1 1 1 www yy com 2 2 2 2 CNAME cname 代表一种映射关系 www yy com www
  • AI芯片面试总结

    基础书籍有哪些 xff1f 重点章节以及概念 xff1f 计算机体系结构 量化研究方法 xff1b 计算机组成与设计 软硬件接口 xff1b deep learning 深度学习 xff1b python xff1b CMOS数字集成电路
  • Android的系统架构

    Android的系统架构采用了分层架构的思想 xff0c 如图1所示 从上层到底层共包括四层 xff0c 分别是应用程序程序层 应用框架层 系统库和Android运行时和Linux内核 图1 xff1a Android系统架构图 每层功能简
  • ensp实验一网络设备基本操作

    实验一 网络设备基本操作 一 实验目的 熟悉网络设备的基本配置 xff1b 掌握网络设备文件系统管理 xff1b 掌握设备的基本调试方法 二 实验学时及环境 1 实验学时 xff1a 2 2 操作系统 xff1a Windows 3 模拟环
  • sudo rosdep init出错 rosdepc update的解决方案

    https mp weixin qq com s VGs8oWdhHH6XsHcx21lN4Q 或者搜索 本文之后 xff0c 世上再无rosdep更新失败问题 xff01 如果有 小鱼就
  • pixhawk学习笔记---创建新的应用程序

    最近转到无人机领域的开发中 xff0c 感觉和以往搞android驱动差别比较大 xff0c 以前搞android驱动的时候网上的资料满天飞 xff0c 但是现在关于飞控相关的资料却少之又少 xff0c 一些资料都是从原理上入手 xff0c
  • 伽马贝塔函数

    在数理方程 概率论等学科经常遇到以下的含参变量的积分 xff0c 它们依次为第一类和第二类欧拉 xff08 Euler 1707 1783瑞士数学家 xff09 积分 xff0c 或依次称为贝塔 xff08 Bata xff09 函数和伽马
  • http-parser用法

    头文件说明 xff1a 解析类型定义 xff1a enum http parser type HTTP REQUEST HTTP RESPONSE HTTP BOTH 解析函数声明 xff1a void http parser init h
  • gazebo崩溃

    1 虚拟机下打开gazebo报错 xff1a VMware vmw ioctl command error Invalid argument INFO 1610283240 619937255 0 180000000 LeePosition
  • k8s中文网站

    https www kubernetes org cn doc 11
  • 【平衡车】PID控制原理到底如何理解?建议收藏!

    文章目录 前言PID算法PID算法的形成P算法 xff0c 即比例控制算法 I算法 xff0c 即积分控制算法D算法 xff0c 即微分控制算法PID总体的数学模型 xff1a 基于单片机的PID控制算法 xff1a 单片机中的PID算法的
  • 嵌入式C语言修炼之道.屏幕操作篇

    汉字处理 现在要解决的问题是 xff0c 嵌入式系统中经常要使用的并非是完整的汉字库 xff0c 往往只是需要提供数量有限的汉字供必要的显示功能 例如 xff0c 一个微波炉的LCD上没有必要提供显示 34 电子邮件 34 的功能 xff1
  • CDN—内容分发网络

    CDN 1 含义 CDN的全称是Content Delivery Network xff0c 即内容分发网络 CDN是构建在现有网络基础之上的智能虚拟网络 xff0c 依靠部署在各地的边缘服务器 xff0c 通过中心平台的负载均衡 内容分发
  • BeautifulSoup

    代码 xff1a from bs4 import BeautifulSoup 一个html格式的内容 doc 61 39 lt html gt lt head gt lt title gt Page title lt title gt lt
  • Ubuntu Server 22.04.1配置(配置root账号、设置固定IP、更改SSH端口、配置UFW、VM扩展磁盘后Ubuntu的扩容)

    为了能快速的创建虚拟机 xff0c 通过VM创建了一个2核CPU 4G内存 40G硬盘 xff0c 安装Ubuntu Server 22 04 1的虚拟机 xff0c 以便在需要的时候随时克隆一个新的虚拟机出来 在新的虚拟机克隆出来后可能会
  • 使用ado连接orical数据库

    使用ADO连接数据库有三种方法 xff1b 方案1 安装Orical数据库软件比方说说oracle 11g R2 32位软件 这里有一个需要注意的地方就是如果你编译的是win32如下图 xff0c 那么就必须要使用32位的数据库软件 其实在
  • QT操作 influxdb时序数据库(libcur)

    概述 最近在项目中需要用到influxdb 数据库 xff0c 当时使用了libcur库之后 xff0c 插入数据的速度一直不太理想 创建字表的速度 1W的话需要11Min xff0c 对于这样的时间完全达不到合格 经过研究进行了打包处理
  • linux中的环境变量

    临时添加环境变量的方法 exprort PATH 61 usr lib PATH export fnp 变量名称 61 变量设置值 参数说明 xff1a f 代表 变量名称 中为函数名称 n 删除指定的变量 变量实际上并未删除 xff0c
  • Linux(openEuler)没有界面连接互联网方法

    前言 系统版本openEuleropenEuler 22 03 LTS x86 64 dvd 我们在安装linux之后 xff0c 一般都是无界面的情况 大部分情况都是需要自己安装界面的 xff0c 如果路由器的情况下直接插上网络就好了 下
  • c#实现内存映射文件共享内存

    内存映射文件是利用虚拟内存把文件映射到进程的地址空间中去 xff0c 在此之后进程操作文件 xff0c 就像操作进程空间里的地址一样了 xff0c 比如使用c语言的 memcpy等内存操作的函数 这种方法能够很好的应用在需要频繁处理一个文件