Delphi保存/加载动态数组失败 [英] Delphi Saving/Loading Dynamic Arrays Failed

查看:213
本文介绍了Delphi保存/加载动态数组失败的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我认为这样做会像我的家庭作业那样是一个问题,但是我仍然在使用复制代码,使用它并尝试了解它'阶段,这是我发现这个主题的最有活力的事情。



我有一个记录:

  type 
Card = record
名称:string;
向上,向右,向左,向下,标记:单个;
IDNumber:Integer;
结束

该记录数组:

  var 
ArrayCard:数组卡;

我想知道如何将这种动态数组存储/加载到/文件。



尝试使用这段代码: http://www.pascalgamedevelopment.com/showthread.php?6319-save-load-a-dynamic-array
像这样:

 过程TMainFrom.WriteMyData; 

Var
FS:TFileStream;
I,iSize:Integer;
TmpPath:string;

开始
TmpPath:= TPath.Combine(TPath.GetDocumentsPath,'Cards.dat');
FS:= TFileStream.Create(TmpPath,fmOpenWrite);
iSize:= Length(ArrayCard);
FS.WriteBuffer(iSize,SizeOf(iSize));
对于I:= 0到iSize - 1 Do
FS.WriteBuffer(ArrayCard [I],SizeOf(Card));
FS.Free;
结束;

它似乎工作到目前为止,但后来我尝试加载它像这样:

 过程TMainFrom.ReadMyData; 

Var
FS:TFileStream;
I,iSize:Integer;
TmpPath:string;
TempCard:卡;

开始
TmpPath:= TPath.Combine(TPath.GetDocumentsPath,'Cards.dat');
FS:= TFileStream.Create(TmpPath,fmOpenRead);
FS.ReadBuffer(iSize,SizeOf(iSize));
SetLength(ArrayCard,iSize);
对于I:= 0到iSize - 1 Do
开始
FS.ReadBuffer(TempCard,SizeOf(Card));
ArrayCard [I]:= TempCard; // It breaks Here ...观看列表:TempCard无法访问的价值
结束;
FS.Free;
结束;

我在模块中收到异常EAccessViolation ...



然后我也尝试过这样的事情: delphi保存并加载动态数组
它加载的数组具有正确的项目数量,但它们都为空或空白:

 程序TMainFrom.SaveCardsToFile; 
var
流:TStream;
L:整数;
TmpPath:string;
ICount:Integer;
strm:TMemoryStream;

begin
TmpPath:= TPath.Combine(TPath.GetDocumentsPath,'Cards.bin');

Stream:= TFileStream.Create(TmpPath,fmCreate);
L:=长度(ArrayCard);
Stream.WriteBuffer(L,SizeOf(L));
Stream.WriteBuffer(指针(ArrayCard)^,L * SizeOf(Card));
Stream.Free;
结束

程序TMainFrom.LoadCardsFromFile;
var
流:TStream;
L:LongWord;
TmpPath:string;

begin
TmpPath:= TPath.Combine(TPath.GetDocumentsPath,'Cards.bin');

Stream:= TFileStream.Create(TmpPath,fmOpenRead);
Stream.ReadBuffer(L,SizeOf(L));
SetLength(ArrayCard,L);
Stream.ReadBuffer(指针(ArrayCard)^,L * SizeOf(Card));
Stream.Free;
结束


解决方案

有一些帮助,我设法重制我的代码正常工作
首先,我需要使字符串 string [20] ,但无法编译android,所以我修改了我的记录,使用数组char 像这样:

 键入
EventString =数组[0..20]的Char;

卡=记录
名称:EventString; // string [20]
向上,向右,向左,向下,标记:单个;
IDNumber:Integer;
结束

然后我修改了我的保存/加载过程,使用TFileStream代替TStream和for循环: p>

 程序TMainFrom.SaveCardsToFile; 
var
流:TFileStream;
L:整数;
TmpPath:string;
n:整数;

begin
TmpPath:= TPath.Combine(TPath.GetDocumentsPath,'Cards.bin');
Stream:= TFileStream.Create(TmpPath,fmCreate);
L:=长度(ArrayCard)-1;
for n:= 0 to L do
begin
Stream.WriteBuffer(ArrayCard [n],SizeOf(Card)); //保存
end;
Stream.Free;
结束

程序TMainFrom.LoadCardsFromFile;
var
流:TFileStream;
L:LongWord;
TmpPath:string;
n:整数;

begin
TmpPath:= TPath.Combine(TPath.GetDocumentsPath,'Cards.bin');
Stream:= TFileStream.Create(TmpPath,fmOpenRead);
SetLength(ArrayCard,Round(Stream.Size / SizeOf(Card)));
L:=长度(ArrayCard)-1;
for n:= 0 to L do
begin
Stream.ReadBuffer(ArrayCard [n],SizeOf(Card)); //加载
ListCard.Items.Add(ArrayCard [n] .Name); //只需将卡名称添加到列表框
end;
Stream.Free;

end;

现在它工作得很好。


I think this will look like 'do my homework' kind of a question, but I'm still at the 'copy code, use it and try to understand it' phase, and this is the most active thing I know of for posting questions of this theme.

I have a record:

type
  Card = record
    Name: string;
    Up,Right,Left,Down,Mark: Single; 
    IDNumber: Integer;
    end;

And array of that record:

var
  ArrayCard: array of Card;

And I wanted to know how can a dynamic array of this kind be stored/loaded to/from a file.

Tried using this piece of code: http://www.pascalgamedevelopment.com/showthread.php?6319-save-load-a-dynamic-array like this:

Procedure TMainFrom.WriteMyData;

  Var
    FS : TFileStream;
    I,iSize : Integer;
    TmpPath: string;

  Begin
    TmpPath:= TPath.Combine(TPath.GetDocumentsPath, 'Cards.dat');
    FS := TFileStream.Create(TmpPath, fmOpenWrite);
    iSize:= Length(ArrayCard);
    FS.WriteBuffer(iSize,SizeOf(iSize));
  For I := 0 To iSize - 1 Do
    FS.WriteBuffer(ArrayCard[I],SizeOf(Card));
  FS.Free;
  End;

An it seems to work so far, but then I try to load it like this:

Procedure TMainFrom.ReadMyData;

  Var
    FS : TFileStream;
    I,iSize : Integer;
    TmpPath: string;
    TempCard : Card;

  Begin
    TmpPath:= TPath.Combine(TPath.GetDocumentsPath, 'Cards.dat');
    FS := TFileStream.Create(TmpPath, fmOpenRead);
    FS.ReadBuffer(iSize,SizeOf(iSize));
    SetLength(ArrayCard,iSize);
  For I := 0 To iSize - 1 Do
    Begin
    FS.ReadBuffer(TempCard,SizeOf(Card));
    ArrayCard[I] := TempCard; //It Breaks Here...The Watch List: TempCard Inaccessible value
    End;
  FS.Free;
  End;

And I get a Exception EAccessViolation in module...

Then I also tried something like this: delphi Save and Load dynamic array It loads the array with the correct amount of items, but they are all empty or blank:

procedure TMainFrom.SaveCardsToFile;
var
  Stream: TStream;
  L: Integer;
  TmpPath: string;
  ICount: Integer;
  strm: TMemoryStream;

begin
  TmpPath:= TPath.Combine(TPath.GetDocumentsPath, 'Cards.bin');

  Stream:= TFileStream.Create(TmpPath, fmCreate);
  L:= Length(ArrayCard);
  Stream.WriteBuffer(L, SizeOf(L));
  Stream.WriteBuffer(Pointer(ArrayCard)^, L * SizeOf(Card));
  Stream.Free;
end;

procedure TMainFrom.LoadCardsFromFile;
var
  Stream: TStream;
  L: LongWord;
  TmpPath: string;

begin
  TmpPath:= TPath.Combine(TPath.GetDocumentsPath, 'Cards.bin');

  Stream:= TFileStream.Create(TmpPath, fmOpenRead);
  Stream.ReadBuffer(L, SizeOf(L));
  SetLength(ArrayCard, L);
  Stream.ReadBuffer(Pointer(ArrayCard)^, L * SizeOf(Card));
  Stream.Free;
end;

解决方案

With some help, I have managed to remake my code to work properly. Firstly I needed to make the string something like string[20] but that couldn't compile for android so I modified my record to use array of char like this:

type
  EventString= array [0..20] of Char;

  Card = record
    Name:  EventString; //string[20]
    Up,Right,Left,Down,Mark: Single;
    IDNumber: Integer;
    end; 

Then I modified my Saving/Loading procedures to use TFileStream instead of TStream and a for loop:

procedure TMainFrom.SaveCardsToFile;
var
  Stream: TFileStream;
  L: Integer;
  TmpPath: string;
  n: Integer;

begin
  TmpPath:= TPath.Combine(TPath.GetDocumentsPath, 'Cards.bin');
  Stream:= TFileStream.Create(TmpPath, fmCreate);
  L:= Length(ArrayCard)-1;
  for n:=0 to L do
  begin
    Stream.WriteBuffer(ArrayCard[n], SizeOf(Card)); //Saving
  end;
  Stream.Free;
end;

procedure TMainFrom.LoadCardsFromFile;
var
  Stream: TFileStream;
  L: LongWord;
  TmpPath: string;
  n: Integer;

begin
  TmpPath:= TPath.Combine(TPath.GetDocumentsPath, 'Cards.bin');
  Stream:= TFileStream.Create(TmpPath, fmOpenRead);
  SetLength(ArrayCard, Round(Stream.Size/SizeOf(Card)));
  L:= Length(ArrayCard)-1;
  for n:=0 to L do
  begin
    Stream.ReadBuffer(ArrayCard[n], SizeOf(Card)); //Loading
    ListCard.Items.Add(ArrayCard[n].Name); //Just adds card names to a listbox
  end;
  Stream.Free;

end;

And now it works just fine.

这篇关于Delphi保存/加载动态数组失败的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

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