Delphi XE5反射中的泛型和JSON序列化

时间:2017-01-16 23:27:53

标签: json delphi

我正在尝试序列化/反序列化以下单元中声明的TMySerializableClass: 单位Unit6; 接口 使用   Winapi.Windows,Winapi.Messages,System.SysUtils,System.Variants,System.Classes,Vcl.Graphics,   Vcl.Controls,Vcl.Forms,Vcl.Dialogs,Vcl.StdCtrls,Generics.Collections,System.SyncObjs,DBXJSon,   DBXJSonReflect; 类型   TForm6 = class(TForm)     Button1:TButton;     备注1:TMemo;     程序Button1Click(发件人:TObject);   私人的   上市     {公开声明}   结束;   TMySerializableClass< T> =班级     MyStringField:string;     MyIntegerField:整数;     MyBooleanField:Boolean;   结束; VAR   Form6:TForm6; 履行 {$ R * .dfm} 程序TForm6.Button1Click(Sender:TObject); VAR   Mar:TJSONMarshal; //串行   UnMar:TJSONUnMarshal; // UnSerializer   SerializedObject:TJSONObject;   aMySerializableClass1:TMySerializableClass< Integer&gt ;;   aMySerializableClass2:TMySerializableClass< Integer&gt ;;   aString:string; 开始   尝试     aMySerializableClass1:= TMySerializableClass< Integer> .Create;     aMySerializableClass2:= TMySerializableClass< Integer> .Create;     Mar:= TJSONMarshal.Create(TJSONConverter.Create);     尝试       SerializedObject:= Mar.Marshal(aMySerializableClass1)为TJSONObject;     最后       Mar.Free;     结束;     Memo1.Text:= SerializedObject.ToString;     // UnMarshalling Kid     UnMar:= TJSONUnMarshal.Create;     尝试       aMySerializableClass2:= UnMar.UnMarshal(SerializedObject)as TMySerializableClass< Integer&gt ;;     最后       UnMar.Free;     结束;   最后     aMySerializableClass1.Free;     aMySerializableClass2.Free;   结束; 结束; 结束。 当我序列化它一切正常,而当反序列化到同一种新的实例化变量时,我得到以下错误: $ 74E5C41F的首次机会异常。消息'内部:无法实例化类型Unit6.TMySerializableClass< System.Integer>'的异常类EConversionError。处理Project7.exe(2252)   编辑:这与TMySerializableClass< T>有关   是通用的。如果我将其声明为TMySerializableClass的话   反序列化工作正常。 想法?

1 个答案:

答案 0 :(得分:0)

无法在XE5上进行测试,但在柏林10.1上我为通用类型的实例添加了别名

后,它对我有用
TMySerializableClassInteger = TMySerializableClass<Integer>;

看起来如果不这样做,Delphi不会生成RTTI信息。

更新。看起来Delphi不需要别名,只是在单元的接口部分有一些专门的类声明。因此,如果您将变量或表单字段声明为TMySerializableClass<Integer>,它也将起作用。