2013-06-01 200 views
1

我用Delphi XE4和超對象1.24超對象多維數組

我有以下結構:

type 
    TMyArray = Array of Array of Variant; 
    TMyRecord = Record 
    Values : TMyArray; 
    end; 

var 
T,W : TMyRecord; 
S : String; 
i : integer; 

begin 
SetLength(T.Values, 2); 
for i := 0 to 1 do 
    SetLEngth(T.Values[i],2); 

T.Values[0,0] := 'Hello World'; 
T.Values[0,1] := 'Foo'; 
T.Values[1,0] := 'Bar'; 
T.Values[1,1] := 'is here'; 

R := TSuperRttiContext.Create; 

S := R.AsJson<TMyRecord>(T).AsString; 
W := R.AsType<TMyRecord>(SO(S)); 
R.Free; 
end; 

S包含{"Values":[["Hello World","Foo"],["Bar","is here"]]}這似乎是正確的

w顯示(((Delphi exception EVariantBadVarTypeError at $294AD325, Variant array of Unknown), (Variant array of Unknown, Variant array of Unknown)))

如何正確地重新創建多維數組?

+0

可以省略用'SetLength(T.Values循環,2,2);'不知道你的問題。 – NGLN

回答

1

我找到了一個方法來實現它。我搜索了很多在谷歌,但我什麼也沒找到,我可以用:( 這裏是我寫的代碼:

// Types and routines 
type 
    TMyArray = Array of Array of Variant; 
    TMyRecord = Record 
    Lines : Integer; 
    Columns : Integer; 
    Values : TMyArray; 
    end; 

function JSONToDynVariantArray(ctx: TSuperRttiContext; const aObj : ISuperObject; 
     var aValue : TValue) : Boolean; 
var 
    i,j: Integer; 
    Row, 
    Col : ISuperObject; 
    SuperType : TSuperType; 

    MyData : TMyRecord; 

begin 
    SuperType := ObjectGetType(aObj); 
    case SuperType of 
    stNull : begin 
     aValue := nil; 
     Result := True; 
    end; 
    stArray : Begin 
    End; 
    stObject : Begin 
     MyData.Lines := aObj.I['Lines']; 
     MyData.Columns := aObj.I['Columns']; 
     SetLength(RecData.Values, MyData.Lines, MyData.Columns); 
     for i := 0 to aObj.A['Values'].Length -1 do begin 
      Row := aObj.A['Values'][i]; 
      for j := 0 to Row.AsArray.Length -1 do begin 
       Col := Row.AsArray[j]; 
       SuperType := ObjectGetType(Col); 
       case SuperType of 
        stNull  : MyData.Values[i,j] := varNull; 
        stBoolean : MyData.Values[i,j] := Col.AsBoolean; 
        stDouble : MyData.Values[i,j] := Col.AsDouble; 
        stCurrency : MyData.Values[i,j] := Col.AsCurrency; 
        stInt  : MyData.Values[i,j] := Col.AsInteger; 
        stString : MyData.Values[i,j] := Col.AsString; 
       end; 
      end; 
     end; 
     TValue.Make(@MyData, Typeinfo(TMyRecord), aValue); 
     Result := True; 
    End; 
    end; 
end; 

// Main code 

var 
    T , 
    W : TMyRecord; 
    S : String; 
    R : TSuperRttiContext; 

begin 
    inherited; 
    T.Lines := 2; 
    T.Columns := 2; 
    SetLength(T.Values, T.Lines,T.Columns); 
    T.Values[0,0] := 'Hello World'; 
    T.Values[0,1] := Date; 
    T.Values[1,0] := 10; 
    T.Values[1,1] := 234.45; 

    R := TSuperRttiContext.Create; 

    // This is a very nice feature!!! 
    R.SerialFromJson.Add(TypeInfo(TMyRecord), JSONToDynVariantArray); 

    S := R.AsJson<TMyRecord>(T).AsString; 
    W := R.AsType<TMyRecord>(SO(S)); 

    R.Free; 
end; 

HTH, 克萊門特