如何读/写超过2 GB的文件? [英] How to read/write to a file which is over the size barrier of 2 GB?
问题描述
因此,我没有一个单一的想法来解决这种情况,我有一个功能可以通过替换我想要的值来修补文件,但是我要修补的文件约为4.5GB.这是功能:
So, i don't have a single idea to get through this situation i have a function that patches a file by replacing the values i want but he file i am trying to patch is about 4.5GB. Here is the function :
private static readonly byte[] PatchFind = { 0x74, 0x72, 0x79 };
private static readonly byte[] PatchReplace = { 0x79, 0x72, 0x74 };
private static bool DetectPatch(byte[] sequence, int position)
{
if (position + PatchFind.Length > sequence.Length) return false;
for (int p = 0; p < PatchFind.Length; p++)
{
if (PatchFind[p] != sequence[position + p]) return false;
}
return true;
}
private static void PatchFile(string originalFile, string patchedFile)
{
// Ensure target directory exists.
var targetDirectory = Path.GetDirectoryName(patchedFile);
if (targetDirectory == null) return;
Directory.CreateDirectory(targetDirectory);
// Read file bytes.
byte[] fileContent = File.ReadAllBytes(originalFile);
// Detect and patch file.
for (int p = 0; p < fileContent.Length; p++)
{
if (!DetectPatch(fileContent, p)) continue;
for (int w = 0; w < PatchFind.Length; w++)
{
fileContent[p + w] = PatchReplace[w];
}
}
// Save it to another location.
File.WriteAllBytes(patchedFile, fileContent);
}
所以我如何实现与2GB +文件一起使用的功能.任何帮助将不胜感激.
So how can i achieve the function to work with 2GB+ files. Any help would be appreciated.
推荐答案
您的问题是 File.ReadAllBytes
不会打开长度大于 Int.MaxValue
的文件.无论文件有多大,仅将整个文件加载到内存中以仅扫描其是否存在模式都是一个糟糕的设计.您应该将文件作为流打开,并使用扫描仪"模式逐步浏览文件,并替换与您的模式匹配的字节.使用 BinaryReader
:
Your problem is that File.ReadAllBytes
will not open files with lengths longer than Int.MaxValue
. Loading an entire file into memory just to scan it for a pattern is a bad design no matter how big the file is. You should open the file as a stream and use the Scanner pattern to step through the file, replacing bytes that match your pattern. A rather simplistic implementation using BinaryReader
:
static void PatchStream(Stream source, Stream target
, IList<byte> searchPattern, IList<byte> replacementPattern)
{
using (var input = new BinaryReader(source))
using (var output = new BinaryWriter(target))
{
var buffer = new Queue<byte>();
while (true)
{
if (buffer.Count < searchPattern.Count)
{
if (input.BaseStream.Position < input.BaseStream.Length)
buffer.Enqueue(input.ReadByte());
else
break;
}
else if (buffer.Zip(searchPattern, (b, s) => b == s).All(c => c))
{
foreach (var b in replacementPattern)
output.Write(b);
buffer.Clear();
}
else
{
output.Write(buffer.Dequeue());
}
}
foreach (var b in buffer)
output.Write(b);
}
}
您可以使用以下代码对文件进行调用:
You can call it on files with code like:
PatchStream(new FileInfo(...).OpenRead(),
new FileInfo(...).OpenWrite(),
new[] { (byte)'a', (byte)'b', (byte)'c' },
new[] { (byte)'A', (byte)'B', (byte)'C' });
这篇关于如何读/写超过2 GB的文件?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!