delphi保存并加载动态数组

Ale*_*xis 3 arrays delphi

请有人帮我保存并从Stream加载其动态数组

const
      iGlobHolderCount = 100;

    type
      TFiLeSpec = record
        iSize: Integer;
      end;

      TFileSpecLst = array of TFiLeSpec;

      TFiLeSpecList = record
        iMin: Integer;
        iMax: Integer;
        iCount: Integer;
        FileSpecLst: TFileSpecLst;
      end;


var
FFileSpec: array of TFiLeSpec;

FFileSpecList: array [1 .. iGlobHolderCount] of TFiLeSpecList;
Run Code Online (Sandbox Code Playgroud)

klu*_*udg 6

首先写入数组的长度,然后写入数组数据:

type
  TItem = Integer;
  TItemArray = array of TItem;

var
  Stream: TStream;
  Arr: TItemArray;
  L: LongWord;

begin
  Arr:= TItemArray.Create(1, 2, 3);
// To save
  Stream:= TFileStream.Create('C:\Temp\test.bin', fmCreate);
  L:= Length(Arr);
  Stream.WriteBuffer(L, SizeOf(L));
  Stream.WriteBuffer(Pointer(Arr)^, L * SizeOf(TItem));
  Stream.Free;
// To load
  Stream:= TFileStream.Create('C:\Temp\test.bin', fmOpenRead);
  Stream.ReadBuffer(L, SizeOf(L));
  SetLength(Arr, L);
  Stream.ReadBuffer(Pointer(Arr)^, L * SizeOf(TItem));
  Stream.Free;
end;
Run Code Online (Sandbox Code Playgroud)


Arn*_*hez 5

从Delphi 5到XE2的另一个解决方案是使用我们的核心OpenSource单元的一些功能.

实际上,它实现了:

  • 一些用于处理记录类型的低级RTTI函数:RecordEquals,RecordSave,RecordSaveLength,RecordLoad;
  • 一个专用的TDynArray对象,它是任何动态数组的包装器,能够在任何动态数组周围显示类似TList的方法,甚至包含记录,字符串或其他动态数组.它能够序列化任何动态数组.
  • 序列化使用优化的二进制格式,并能够将任何记录或动态数组保存并加载为RawByteString.

你可以编码,例如

var
  FFileSpec: array of TFiLeSpec;
  TFileSpecList = array of TFiLeSpecList;
  FFileSpecList: TFileSpecList;

var FSL: TDynArray;
    Bin: RawByteString;
begin
  FSL.Init(TypeInfo(TFiLeSpecList),FFileSpecList);
  // ... then you use FFileSpecList[] as usual
  // ... or use some methods of FSL:
  if FSL.Count>0 then
    FSL.Delete(0);
  FSL.Add(FFileSpec);
  FSL.Clear;
  // then you can serialize the content to binary
  Bin := FSL.SaveTo;
  // use FSL.LoadFrom(Bin) to read the whole array content back
  // or you can use a TStream 
  FSL.SaveToStream(aStream); 
  FSL.Clear;
  aStream.Position := 0;
  FSL.LoadFrom(aStream);
  // you do not need to release nor Free FSL: this is a wrapper around FFileSpecList
end;
Run Code Online (Sandbox Code Playgroud)

请注意,我已经用TFileSpecList动态数组替换了你,但你可以使用固定数组,在记录中提供额外的RTTI - 然后使用RecordLoad / RecordSave函数.它将使用RTTI(即使使用Delphi 5)保存内部动态数组内容,处理其中的任何string或嵌套数组.

它由我们的mORMot框架使用(例如,用于动态数组序列化到DB中),但它不是它的一部分:只需要一个单元,也不需要SQLite3,也不需要整个ORM类.

有关其他信息,请参阅此页面.