(宽)字符串 - 存储在TFileStream,Delphi 7.什么是最快的方式? [英] (Wide)String - storing in TFileStream, Delphi 7. What is the fastest way?

查看:272
本文介绍了(宽)字符串 - 存储在TFileStream,Delphi 7.什么是最快的方式?的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我使用Delphi7(非unicode VCL),我需要在TFileStream中存储很多WideStrings。我不能使用TStringStream作为(宽)字符串与二进制数据混合,该格式被预计加速加载和写入数据...但是我相信当前正在加载/写入字符串可能是一个我的代码的瓶颈...

I'm using Delphi7 (non-unicode VCL), I need to store lots of WideStrings inside a TFileStream. I can't use TStringStream as the (wide)strings are mixed with binary data, the format is projected to speed up loading and writing the data ... However I believe that current way I'm loading/writing the strings might be a bottleneck of my code ...

目前我正在写一个字符串的长度,然后通过char ...
写入它,加载时,首先我'加载长度,然后通过char加载char ...

currently I'm writing length of a string, then writing it char by char ... while loading, first I'm loading the length, then loading char by char ...

那么,保存和加载WideString到TFileStream的最快方法是什么?

So, what is the fastest way to save and load WideString to TFileStream?

提前感谢

推荐答案

而不是一次读写一个字符,一次写入它们:

Rather than read and write one character at a time, read and write them all at once:

procedure WriteWideString(const ws: WideString; stream: TStream);
var
  nChars: LongInt;
begin
  nChars := Length(ws);
  stream.WriteBuffer(nChars, SizeOf(nChars);
  if nChars > 0 then
    stream.WriteBuffer(ws[1], nChars * SizeOf(ws[1]));
end;

function ReadWideString(stream: TStream): WideString;
var
  nChars: LongInt;
begin
  stream.ReadBuffer(nChars, SizeOf(nChars));
  SetLength(Result, nChars);
  if nChars > 0 then
    stream.ReadBuffer(Result[1], nChars * SizeOf(Result[1]));
end;

从技术上讲,由于 WideString 是Windows BSTR ,它可以包含一个奇数字节数。 Length 函数读取字节数并将其除以2,所以可能(尽管不太可能)上面的代码将会切断最后一个字节,您可以使用此代码:

Now, technically, since WideString is a Windows BSTR, it can contain an odd number of bytes. The Length function reads the number of bytes and divides by two, so it's possible (although not likely) that the code above will cut off the last byte. You could use this code instead:

procedure WriteWideString(const ws: WideString; stream: TStream);
var
  nBytes: LongInt;
begin
  nBytes := SysStringByteLen(Pointer(ws));
  stream.WriteBuffer(nBytes, SizeOf(nBytes));
  if nBytes > 0 then
    stream.WriteBuffer(Pointer(ws)^, nBytes);
end;

function ReadWideString(stream: TStream): WideString;
var
  nBytes: LongInt;
  buffer: PAnsiChar;
begin
  stream.ReadBuffer(nBytes, SizeOf(nBytes));
  if nBytes > 0 then begin
    GetMem(buffer, nBytes);
    try
      stream.ReadBuffer(buffer^, nBytes);
      Result := SysAllocStringByteLen(buffer, nBytes)
    finally
      FreeMem(buffer);
    end;
  end else
    Result := '';
end;

灵感来自 Mghie的答案已经替换了我的 Read 使用 ReadBuffer WriteBuffer 编写。如果他们无法读取或写入请求的字节数,后者将引发异常。

Inspired by Mghie's answer, have replaced my Read and Write calls with ReadBuffer and WriteBuffer. The latter will raise exceptions if they are unable to read or write the requested number of bytes.

这篇关于(宽)字符串 - 存储在TFileStream,Delphi 7.什么是最快的方式?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆