【问题标题】:Class with builtin marshalling. Why are the field converters not working?具有内置编组的类。为什么现场转换器不工作?
【发布时间】:2011-09-30 09:26:33
【问题描述】:

我有以下问题:

  1. 是否应该将编组放置在类助手中?或者把它放在课堂“里面”就可以了吗?
  2. 为什么现场转换器不工作?

使用 Delphi XE - 考虑一下:

type
  TMyClass = Class
  public
    FaString : String;
    FaStringList : TStringList; 
    FMar : TJsonMarshal;
    procedure RegisterConverters;
    function Marshal : TJsonObject;  // should handle marshalling
  end;

RegisterConverters 看起来像这样。

procedure TMyClass.RegisterConverters;
begin
  // try and catch the marshaller itself.
  FMar.RegisterConverter(TJsonMarshal, 'FMar',
    function(Data : TObject; Field:String): TObject
    begin
      Exit(nil); // Since we cannot marshal it - and we dont need it anyways.
    end);
  // catch TStringList
  FMar.RegisterConverter(TStringList, 'FaStringList',
    function(Data: TObject; Field:String): TListOfStrings
    var
      i, count: integer;
    begin
      count := TStringList(Data).count;
      SetLength(Result, count);
      for i := 0 to count - 1 do
        Result[i] := TStringList(Data)[i];
    end);
end; 

还有元帅法:

function TMyClass.Marshal: TJSONObject;
begin
  if FMar = nil then
    FMar := TJSONMarshal.Create(TJSONConverter.Create);
  try
    RegisterConverters;
    try
      Result := FMar.Marshal(Self) as TJSONObject;
    except
      Result := nil;
    end;
  finally
    FMar.Free;
  end;
end;

那么我们可以这样做:

var
  aObj : TMyClass;
  ResultString : String;
begin
  aObj := TMyClass.Create;
  aObj.FaString := 'Test string';
  aObj.FaStringList := TStringList.Create;
  aObj.FaStringList.Add('stringliststring #1');
  aObj.FaStringList.Add('stringliststring #2');
  aObj.FaStringList.Add('stringliststring #3');
  aObj.FaStringList.Add('stringliststring #4');

  // StringList and JsonMarshal should be handled by converter
  ResultString := (aObj.Marshal).ToString;
end;

但我根本无法让它工作。字段转换器没有被触发?

我在这里做错了吗?或者我应该看一下我的 Delphi XE 安装(可能是被骗了)?

【问题讨论】:

  • 我找到了解决方案...从“内部”执行封送处理时,您必须正确设置它:-) procedure TMyClass.RegisterConverters; begin // try and catch the marshaller itself. FMar.RegisterConverter(ClassType, 'FMar', // catch TStringList FMar.RegisterConverter(ClassType, 'FaStringList', 不同之处在于使用 ClassType 作为调用中的类型注册转换器。否则无法到达指定的字段 - 我应该看到的!
  • 您可以将此作为答案发布(稍后也接受)
  • 发帖后 8 小时不能 - 我的代表太低 :-) 但我会 - 在时间限制允许的情况下。

标签: delphi marshalling delphi-xe converter


【解决方案1】:

当从“内部”做marshal时,你必须正确设置它:-)

procedure TMyClass.RegisterConverters;
begin
  // try and catch the marshaller itself.
  FMar.RegisterConverter(ClassType, 'FMar',
    function(Data : TObject; Field:String): TObject
    begin
      Exit(nil); // Since we cannot marshal it - and we dont need it anyways.
    end);
  // catch TStringList
  FMar.RegisterConverter(ClassType, 'FaStringList',
    function(Data: TObject; Field:String): TListOfStrings
    var
      i, count: integer;
    begin
      count := TStringList(Data).count;
      SetLength(Result, count);
      for i := 0 to count - 1 do
        Result[i] := TStringList(Data)[i];
    end);
end; 

不同之处在于使用 ClassType 作为对 RegisterConverter 的调用中的类型。 否则无法到达指定的字段 - 我应该看到的!

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2011-01-19
    • 2011-10-10
    • 2018-01-15
    • 2021-05-22
    • 1970-01-01
    • 2020-10-27
    相关资源
    最近更新 更多