BinaryReader 在第一个 运行 之后快了 30 倍。字节数组还在内存中?
BinaryReader 30x faster after first run. Byte array still in memory?
我的程序从文件中读取 x 个字节,检查它们是否全为零,对 20.000 个文件重复该过程,并保留具有非零字节的文件列表。
为了监控性能,我将它检查的每个文件的字节数定义为 (byteSize)。
问题是程序的第一个 运行 需要大约 5 分钟才能完成 (byteSize = 8192),但是如果我再次 运行 它只需要 10 秒,即使我关闭并重新启动程序,所以我想到的唯一原因是字节数组保留在内存中。
BinaryReader 在 "using" 指令下,据我所知它应该在循环完成后关闭流。那么为什么字节数组仍然存在呢?我怎样才能删除它?我需要在每次 运行 程序时测量实际性能。
byte[] readByte = new byte[byteSize];
for (int i = 0; i < readCycles; i++)
{
using (BinaryReader reader = new BinaryReader(new FileStream(file, FileMode.Open, FileAccess.Read)))
{
reader.BaseStream.Seek(8192 + i * byteSize, SeekOrigin.Begin);
reader.Read(readByte, 0, byteSize);
}
foreach (byte b in readByte)
{
if (b != 0)
{
allZeros = false;
break;
}
else
allZeros = true;
}
if (allZeros == false) break;
}
这几乎可以肯定与 .NET 正在做的任何事情无关 - 它是文件系统为您透明地缓存。
要对此进行测试,请将您的代码更改为仅使用 FileStream
并简单地将文件循环读取到缓冲区并忽略数据:
using (var stream = File.OpenRead(...))
{
var buffer = new byte[16384];
while (stream.Read(buffer, 0, buffer.Length) > 0)
{
}
}
我相信您会看到相同的结果 - 第一次读取会相对较慢,然后会很快。
我的程序从文件中读取 x 个字节,检查它们是否全为零,对 20.000 个文件重复该过程,并保留具有非零字节的文件列表。 为了监控性能,我将它检查的每个文件的字节数定义为 (byteSize)。
问题是程序的第一个 运行 需要大约 5 分钟才能完成 (byteSize = 8192),但是如果我再次 运行 它只需要 10 秒,即使我关闭并重新启动程序,所以我想到的唯一原因是字节数组保留在内存中。
BinaryReader 在 "using" 指令下,据我所知它应该在循环完成后关闭流。那么为什么字节数组仍然存在呢?我怎样才能删除它?我需要在每次 运行 程序时测量实际性能。
byte[] readByte = new byte[byteSize];
for (int i = 0; i < readCycles; i++)
{
using (BinaryReader reader = new BinaryReader(new FileStream(file, FileMode.Open, FileAccess.Read)))
{
reader.BaseStream.Seek(8192 + i * byteSize, SeekOrigin.Begin);
reader.Read(readByte, 0, byteSize);
}
foreach (byte b in readByte)
{
if (b != 0)
{
allZeros = false;
break;
}
else
allZeros = true;
}
if (allZeros == false) break;
}
这几乎可以肯定与 .NET 正在做的任何事情无关 - 它是文件系统为您透明地缓存。
要对此进行测试,请将您的代码更改为仅使用 FileStream
并简单地将文件循环读取到缓冲区并忽略数据:
using (var stream = File.OpenRead(...))
{
var buffer = new byte[16384];
while (stream.Read(buffer, 0, buffer.Length) > 0)
{
}
}
我相信您会看到相同的结果 - 第一次读取会相对较慢,然后会很快。