MemoryStream和BufferedStream都派生自基类Stream,因此它们有很多共同的属性和方法,但是每一个类都有自己独特的用法。这两个类都是实现对内存进行数据读写的功能,而不是对持久性存储器进行读写。

读写内存-MemoryStream类

MemoryStream类用于向内存而不是磁盘读写数据。MemoryStream封装以无符号字节数组形式存储的数据,该数组在创建MemoryStream对象时被初始化,或者该数组可创建为空数组。可在内存中直接访问这些封装的数据。内存流可降低应用程序中对临时缓冲区和临时文件的需要。

下表列出了MemoryStream类的重要方法:

1、Read():读取MemoryStream流对象,将值写入缓存区。

2、ReadByte():从MemoryStream流中读取一个字节。

3、Write():将值从缓存区写入MemoryStream流对象。

4、WriteByte():从缓存区写入MemoytStream流对象一个字节。

Read方法使用的语法如下:

mmstream.Read(byte[] buffer,offset,count) 

其中mmstream为MemoryStream类的一个流对象,3个参数中,buffer包含指定的字节数组,该数组中,从offset到(offset +count-1)之间的值由当前流中读取的字符替换。Offset是指Buffer中的字节偏移量,从此处开始读取。Count是指最多读取的字节数。Write()方法和Read()方法具有相同的参数类型。

MemoryStream类的使用实例:

using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.IO;namespace ConsoleApplication1
{class Program{static void Main(){ int count; byte[] byteArray; char[] charArray;UnicodeEncoding uniEncoding = new UnicodeEncoding();// Create the data to write to the stream.byte[] firstString = uniEncoding.GetBytes("一二三四五"); byte[] secondString = uniEncoding.GetBytes("上山打老虎"); using (MemoryStream memStream = new MemoryStream(100)){ // Write the first string to the stream.memStream.Write(firstString, 0, firstString.Length); // Write the second string to the stream, byte by byte.count = 0;while (count < secondString.Length) {memStream.WriteByte(secondString[count++]); } // Write the stream properties to the console.Console.WriteLine("Capacity={0},Length={1},Position={2}\n", memStream.Capacity.ToString(), memStream.Length.ToString(), memStream.Position.ToString());// Set the position to the beginning of the stream.memStream.Seek(0, SeekOrigin.Begin);// Read the first 20 bytes from the stream.byteArray = new byte[memStream.Length]; count = memStream.Read(byteArray, 0, 20); // Read the remaining bytes, byte by byte.while (count < memStream.Length) { byteArray[count++] = Convert.ToByte(memStream.ReadByte());} // Decode the byte array into a char array// and write it to the console.charArray = new char[uniEncoding.GetCharCount(byteArray, 0, count)]; uniEncoding.GetDecoder().GetChars(byteArray, 0, count, charArray, 0); Console.WriteLine(charArray); Console.ReadKey();}}}
}

在这个实例代码中使用了using关键字。注意:

using 关键字有两个主要用途:

1、作为指令,用于为命名空间创建别名或导入其他命名空间中定义的类型。

例如: using System;

2、作为语句,用于定义一个范围,在此范围的末尾将释放对象。

using(Connection conn=new Connection(connStr))
{
}
//使用using关键字可及时销毁对象 

MemoryStream.Capacity 属性 取得或设定配置给这个资料流的位元组数目。

MemoryStream.Position 属性 指定当前流的位置。

MemoryStream.Length 属性获取用字节表示的流长度。

SeekOrigin()是一个枚举类,作用设定流的一个参数。

SeekOrigin.Begin我得理解就是文件的最开始,“0”是偏移,表示跳过0个字节。写2就是跳过2个字节。

MemoryStream类通过字节读写数据。本例中定义了写入的字节数组,为了更好的说明Write和WriteByte的异同,在代码中声明了两个byte数组,其中一个数组写入时调用Write方法,通过指定该方法的三个参数实现如何写入。

另一个数组调用了WriteByte方法,每次写入一个字节,所以采用while循环来完成全部字节的写入。写入MemoryStream后,可以检索该流的容量,实际长度,当前流的位置,将这些值输出到控制台。通过观察结果,可以确定写入MemoryStream流是否成功。

调用Read和ReadByte两种方法读取MemoryStream流中的数据,并将其进行Unicode编码后输出到控制台。

读取内存流中的数据

在.NET中,使用抽象基类System.IO.Stream代表流,它提供Read和Write两个方法。由于数据流的有序性,因此流对象还有一个读写指针,为此,Stream类还有一个Seek方法用于移动读写指针。

字符串与字节数组间的互相转化:

        string str = "内存大小";byte[] temp = Encoding.UTF8.GetBytes (str);        // 字符串转化为字节数组string s = Encoding.UTF8.GetString (temp);        // 字节数组转化为字符串Debug.Log (s);

Encoding用法比较简单,如果只是字节和字符的互相转换,GetBytes()和GetChars()这两个方法及它们的重载基本上会满足你所有要求。

GetByteCount()及其重载是得到一个字符串转换成字节时实际的字节个数。

GetCharCount()及其重载是得到一个字节数组转换成字符串的大小。

Decoder.GetChars 方法

Decoder.GetChars (Byte[], Int32, Int32, Char[], Int32)

在派生类中重写时,将指定字节数组的字节序列和内部缓冲区中的任何字节解码到指定的字符数组。

在派生类中重写时,将一个字节序列解码为一组字符。

Java里一个byte取值范围是-128~127, 而C#里一个byte是0~255.

首位不同. 但是底层I/O存储的数据是一样的

FileStream对象的数据来自文件,而MemoryStream对象的数据来自内存缓冲区。这两个类都继承自Stream类。

MemoryStream的数据来自内存中的一块连续区域,这块区域称为“缓冲区(Buffer)”。可以把缓冲区看成一个数组,每个数组元素可以存放一个字节的数据。

在创建MemoryStream对象时,可以指定缓冲区的大小,并且可以在需要的时候更改。//字节数组byte[] buffer = new byte[600];//填充字节数组private void CreateExampleData(){for(int i=0; i<600; i++){//byte类型的数最大不能超过255,用256取模实现buffer[i] = (byte)(i%256);}            }
内存流的基本使用方法:private void OnTestMemory(){//创建测试数据CreateExampleData();//创建内存流对象,初始分配50字节的缓冲区MemoryStream mem = new MemoryStream(50);//向内存流中写入字节数组的所有数据mem.Write(buffer,0,buffer.GetLength(0));MessageBox.Show("写入数据后的内存流长度:" + mem.Length.ToString());MessageBox.Show("分配给内存流的缓冲区大小:" + mem.Capacity.ToString());mem.SetLength(550);MessageBox.Show("调用SetLength方法后的内存流长度:" + mem.Length.ToString());mem.Capacity = 620;//此值不能小于Length属性MessageBox.Show("调用Capacity方法后缓冲区大小:" + mem.Capacity.ToString());//将读写指针移到距流开头10个字节的位置mem.Seek(10,SeekOrigin.Begin);MessageBox.Show(mem.ReadByte().ToString());mem.Close();}
内存流的Length属性代表了其中存放的数据的真实长度,而Capacity属性则代表了分配给内存流的内存空间大小。
可以使用字节数组创建一个固定大小的MemoryStream,MemoryStream mem = new MemoryStream(buffer);
这时,无法再设置Capacity属性的大小。
还可以创建只读的内存流对象。MemoryStream mem = new MemoryStream(buffer,false);FlieStream用于存取文件。
创建文件并写入内容://创建一个新文件FileStream fsForWrite = new FileStream("test.data",FileMode.Create);try{    //写入一个字节fsForWrite.WriteByte(100);CreateExampleData();//将字节数组写入文件fsForWrite.Write(buffer,0,buffer.GetLength(0));}catch(Exception ex){    MessageBox.Show(ex.Message);}finally{//关闭文件fsForWrite.Close();}
打开文件并读取内容:private void ReadFromFile(){FileStream fsForRead = new FileStream("test.data",FileMode.Open);try{//读入一个字节MessageBox.Show("文件的第一个字节为:"+fsForRead.ReadByte().ToString());//读写指针移到距开头10个字节处fsForRead.Seek(10,SeekOrigin.Begin);byte[] bs = new byte[10];//从文件中读取10个字节放到数组bs中fsForRead.Read(bs,0,10);}catch(Exception ex){    MessageBox.Show(ex.Message);}finally{fsForRead.Close();         }}
如果一个程序退出了,但它打开的文件没有被关闭,将导致其他程序无法修改或删除此文件。
FileStream与MemoryStream间的相互作用:
-----解决方案--------------------
  FileStream fs = new FileStream(path, FileMode.Open); byte[] data = new byte[fs.Length]; fs.Read(data, 0, data.Length); fs.Close();MemoryStream ms = new MemoryStream(data);
 ///定义并实例化一个内存流,以存放图片的字节数组。 MemoryStream m = new MemoryStream(); ///获得当前路径 string strAppPath = AppDomain.CurrentDomain.BaseDirectory; //获得可执行文件的路径。 ///获得图片路径  string strPath = strAppPath + "img\\default.jpg";  ///图片读入FileStream  FileStream f = new FileStream(strPath, FileMode.open);  ///把FileStream写入MemoryStream  m.SetLength(f.Length);  f.Read(m.GetBuffer(), 0, (int)f.Length);  m.Flush();  f.Close(); 
FileStream fs = new FileStream(fileName, FileMode.Open);
byte[] MyData = new byte[fs.Length];
fs.Read(MyData, 0, (int)fs.Length);
fs.Close();
MemoryStream ms = new MemoryStream(MyData);
MemoryStream ms = new MemoryStream(File.ReadAllBytes("c:\\1.jpg"));

使用MemoryStream类读写内存相关推荐

  1. java memorystream 包_C#使用MemoryStream类读写内存

    和FileStream一样,MemoryStream和BufferedStream都派生自基类Stream,因此它们有很多共同的属性和方法,但是每一个类都有自己独特的用法.这两个类都是实现对内存进行数 ...

  2. C#中MemoryStream类的介绍

    MemoryStream位于System.IO命名空间,为系统内存提供流式的读写操作.常作为其他流数据交换时的中间对象操作. 1.MemoryStream类封装一个字节数组,在构造实例时可以使用一个字 ...

  3. 字节终面:CPU 是如何读写内存的?

    如果你觉得这是一个非常简单的问题,那么你真应该好好读读本文,我敢保证这个问题绝没有你想象的那么简单. 注意,一定要完本文,否则可能会得出错误的结论. 闲话少说,让我们来看看CPU在读写内存时底层究竟发 ...

  4. MemoryStream类

    MemoryStream 是一个特例,MemoryStream中没有任何非托管资源,所以它的Dispose不调用也没关系.托管资源.Net会自动回收 MemoryStream继承自Stream类.内存 ...

  5. Properties类读写配置文件

    Properties类读写简单配置文件相当的方便,以前竟然没注意到这个类. FileInputStream fs = new FileInputStream("config.ini" ...

  6. 如何实现流畅观影体验?视频类应用内存和CPU大调查

    如果把手机内存和CPU想象成固定面积的田地,单个应用对内存和CPU的占用则可比喻为个人的一亩三分地儿.当应用内存和CPU占用过高时,便过多占用了整个田地资源,挤压了邻家应用的面积,那么手机能够同时运行 ...

  7. C++ 类的内存分布

    C++类内存分布 转自:http://www.cnblogs.com/jerry19880126/p/3616999.html 先写下总结,通过总结下面的例子,你就会明白总结了. 下面总结一下: 1. ...

  8. 静态成员变量不占用类的内存空间

    假定程序运行环境为:操作系统Windows 2000,VC6.0编译环境,X86(80586)CPU处理器(32位小字节序处理器,4字节对齐) class CExample { public:     ...

  9. 【Android 逆向】代码调试器开发 ( 代码调试器功能简介 | 设置断点 | 读写内存 | 读写寄存器 | 恢复运行 | Attach 进程 )

    文章目录 一.代码调试器功能简介 二.Attach 进程 一.代码调试器功能简介 代码调试器功能 : 设置断点 : 无论什么类型的调试器 , 都必须可以设置断点 , 运行到断点处 , 挂起被调试进程 ...

最新文章

  1. YOLOv3 best_iou问题
  2. How to tell if UIViewController's view is visible
  3. ios 监听TextField中内容变化
  4. android 数据存储路径
  5. 日常方便使用的Python脚本实现
  6. 路由相关知识,静态路由、默认路由、浮动路由的概念以及基本设置
  7. php 如何获取表格数据类型,使用phpword获取doc中的表格数据
  8. apache pdfbox_Apache PDFBox 2
  9. java修改另存excel_Word文档导入Excel总变形,调整格式你花了1小时,同事三步就搞定...
  10. 摘抄 ander图片上传
  11. 沙盒技术——selinux控制
  12. 文法规则自顶向下分析
  13. 上传叶绿体基因组序列至NCBI
  14. 如何解决Mac电脑没声音了的问题
  15. 我以为我会junit,原来我还不会
  16. STM32---定时器的ETR功能
  17. 中国移动发狠,给携转用户巨额优惠,反击中国电信
  18. 投资银行业务过关必做1500题
  19. 开启多媒体台式计算机过程,东师多媒体计算机技术19秋在线作业2题目【标准答案】...
  20. CS4398 Cirrus Logic的旗舰级音频解码芯片

热门文章

  1. oracle-ora 各种sql异常描述
  2. JetLinks学习笔记一
  3. 解决:微信小程序只有调试或真机打开调试模式时可以访问网络,手机预览不能访问网络
  4. 云计算发展前景好不好 学了后能胜任哪些岗位
  5. 北京信息科技大学考研c语言考试,2018年北京信息科技大学计算机院814数据结构和C语言程序设计[专硕]之C程序设计考研核心题库...
  6. EOFError: marshal data too short
  7. nutch java_Nutch:用Java调用,而不是命令行?
  8. selenium抓取斗鱼直播平台数据
  9. Arduino使用敲击模块和光遮断
  10. TI公司三大系列DSP内部结构之比较