Byte [stream.length]-内存不足异常,最好的解决方法?

问题描述 投票:0回答:3

我正在尝试从文件中读取字节流。但是,当我尝试读取字节时,我得到了

由于内存不足,功能评估被禁用例外

非常简单。但是,解决此问题的最佳方法是什么?是否一次也围绕1028的长度循环?还是有更好的方法?

我正在使用的C#

BinaryReader br = new BinaryReader(stream fs);

// The length is around 600000000
long Length = fs.Length;

// Error here
bytes = new byte[Length];

for (int i = 0; i < Length; i++)
{
   bytes [i] = br.ReadByte();
}

谢谢

c# stream binaryreader
3个回答
3
投票

嗯。首先。想象一个文件的大小例如2GB。您的代码将分配2GB的内存。只需读取您真正需要的文件部分,而不是一次读取整个文件。其次:不要做这样的事情:

for (int i = 0; i < Length; i++)
{
   bytes [i] = br.ReadByte();
}

效率很低。要读取流的原始字节,应使用类似以下内容的方法:

using(var stream = File.OpenRead(filename))
{
    int bytesToRead = 1234;
    byte[] buffer = new byte[bytesToRead];

    int read = stream.Read(buffer, 0, buffer.Length);

    //do something with the read data ... e.g.:
    for(int i = 0; i < read; i++)
    {
        //...
    }
}

0
投票

[当您尝试分配数组时,CLR将其连续放置在OS分配给它的虚拟内存中。但是,虚拟内存可以分段,因此可能无法使用连续的1 GB块,因此出现OutOfMemoryException。您的计算机有多少物理RAM无关紧要,并且此问题不仅限于托管代码(尝试在本机C中分配一个巨大的数组,您会发现类似的结果)。

[我建议不要使用几个较小的数组,而不是分配一个巨大的数组,一个ArrayList或List,这样框架就可以按块分配数据。

希望有所帮助


0
投票

我相信,流对象的实例化已经将文件读入了缓存中。然后循环将内存中的字节复制到另一个数组。

© www.soinside.com 2019 - 2024. All rights reserved.