我有一个使用TStringList的备份系统,但是我用旧的Delphi(Ansi字符串)编码。从旧版本到最新版本的TStringList备份的兼容性
基本上我有此当我保存:
...
MyStringList.SaveToStream(Str);
StrSz := Str.Size;
MyBackupStream.Write(StrSz, SizeOf(Integer));
MyBackupStream.Write(Str.Memory^, StrSz);
...
,当我重新加载:
...
MyBackupStream.Read(StrSz, SizeOf(Integer));
Str.SetSize(StrSz);
MyBackupStream.Read(Str.Memory^, StrSz);
MyStringList.SetText := PChar(Str.Memory);
...
我用这个顺序(大小+命令datasize字节,则大小+命令datasize字节等)系统用于各种组件备份。事实上,在stringlist备份之前(我的意思是在StringList备份之前和之后有一些数据)之前,一些东西总是被'读取'或'写入'。
我在这里引入了一个大问题(如果我切换到现代的Delphi版本)? 在未来的delphi版本中,块仍然可以被castable(如果我切换?)。我需要在备份头文件中写入字符串版本吗?
不幸的是我无法测试这个。我认为,如果我至少在头文件中编写字符串编码类型,那么以后我可以用正确的方式将其转换,无论是什么版本的Delphi,不是吗?
当我使用loadfromstream我得到AV。我在之前的项目中注意到了这一点,对于我来说,使用TStringList.SaveToStream保存数据的唯一方法是将保存的数据作为字符串进行投射,如我的示例中所做的那样。我知道这很奇怪,但我不能用另一种方式来做... – az01
AV意味着你正在访问无效的内存。 TStringList指针或TStream指针无效。正确使用时,LoadFromStream()工作得很好。我从来没有在任何版本中使用AV。如果你必须演员,那么你需要做的比你之前展示的更安全。你显示的内容不安全。它访问不属于TStream的周围内存。 –
我已经将您的答案标记为已接受,但更多要关闭该主题。在我的备份流中,我有一个版本号。即使没有人在这里明确地告诉我,我将能够在最新版本的软件中投入旧数据,但我认为没关系。但是你把重点放在我重新加载字符串的方式上。对我来说,这是好事...我不期待这样的评论... – az01