Delphi 11 10 XE8 XE7 XE Seattle Berlin Tokyo Rio Firemonkey, Delphi Android, Delphi IOS

Four Ways To Parse JSON Into Objects With Delphi XE6 Firemonkey On Android And IOS

| Delphi 11 10 XE8 XE7 XE Seattle Berlin Tokyo Rio Firemonkey Delphi Android Delphi IOS

Delphi XE6 Firemonkey Parse J | Delphi 11 10 XE8 XE7 XE Seattle Berlin Tokyo Rio Firemonkey Delphi Android Delphi IOSStephen Bell from Embarcadero recently posted a blog post on how to parse JSON with a single line of code in Delphi XE6 Firemonkey. I had to parse some JSON recently myself and I wanted to try out some different ways of doing that as I usually use XSuperObject. I came up with four different ways to parse out a piece of JSON. Some of the ways are completely static and one of them is completely dynamic. The four ways I tried are the TJson.JsonToObject way into a custom object, using the straight XSuperObject way into a custom object, using XSuperObject into a generic Tuple, and using XSuperObject into a dynamic TStringList. When I parse the JSON I put the object that I create to store the data in into a TStringList for usage later. Full source code for a sample project demonstrating each way is available at the bottom. All four ways will probably also work in Delphi XE5 and AppMethod in addition to cross platform on Windows, OSX, Android, and IOS.

Here is the straight XSuperObject into a custom object. This way is pretty static and requires that you define an object, TPizza, in the type section:
TPizza = class(TObject)
public
FName: string;
FTopping1: string;
FTopping2: string;
FTopping3: string;
end;

function TForm1.GetJsonValue(obj:ISuperObject; Name: String): String;
begin
Result := '';
if obj.Contains(Name) then
Result := obj.S[Name];
end;

procedure TForm1.LoadJSONXSuperObject(S: String);
var
aobj: ISuperArray;
obj, obj2: ISuperObject;
I, II: Integer;
Pizza: TPizza;
begin

aobj := SA(S);
for I := 0 to aobj.Length-1 do
begin
obj2 := aobj.O[I];

Pizza := TPizza.Create;
Pizza.FName := GetJsonValue(obj2,'Name');
Pizza.FTopping1 := GetJsonValue(obj2,'Topping1');
Pizza.FTopping2 := GetJsonValue(obj2,'Topping2');
Pizza.FTopping3 := GetJsonValue(obj2,'Topping3');
PizzaList.AddObject(Pizza.FName, Pizza);
end;
end;
Here is the TJson.JsonToObject into a custom object. This way takes less code than the direct XSuperObject way but still requires that you define an object, TPizza, in the type section:
TPizza = class(TObject)
public
FName: string;
FTopping1: string;
FTopping2: string;
FTopping3: string;
end;

procedure TForm1.LoadJSONToObject(S: String);
var
aobj: ISuperArray;
obj, obj2: ISuperObject;
I, II: Integer;
Pizza: TPizza;
begin

aobj := SA(S);
for I := 0 to aobj.Length-1 do
begin
obj2 := aobj.O[I];

Pizza := TJson.JsonToObject<TPizza>(obj2.AsJSON);
PizzaList.AddObject(Pizza.FName, Pizza);
end;
end;

 
And here is reading both of the above back out from the TPizza object:
for I := 0 to PizzaList.Count-1 do
begin
Memo2.Lines.Append('Name: ' + TPizza(PizzaList.Objects[I]).FName);
Memo2.Lines.Append('Topping1: ' + TPizza(PizzaList.Objects[I]).FTopping1);
Memo2.Lines.Append('Topping2: ' + TPizza(PizzaList.Objects[I]).FTopping2);
Memo2.Lines.Append('Topping3: ' + TPizza(PizzaList.Objects[I]).FTopping3);
end;

Here is the XSuperObject into a Tuple. For me this code is harder to read but does not require that you define the extra TPizza object type at the top of the unit:
procedure TForm1.LoadJSONXSuperObjectTuple(S: String);
var
aobj: ISuperArray;
obj, obj2: ISuperObject;
I, II: Integer;
Pizza: TTuple<String, String, String, String>;
begin

aobj := SA(S);
for I := 0 to aobj.Length-1 do
begin
obj2 := aobj.O[I];

for II := 0 to obj2.Count-1 do
begin
Pizza := TTuple<String, String, String, String>.Create(
GetJsonValue(obj2,'Name'),
GetJsonValue(obj2,'Topping1'),
GetJsonValue(obj2,'Topping2'),
GetJsonValue(obj2,'Topping3')
);

obj2.Next;
end;
PizzaList.AddObject(Pizza.Value1, Pizza);
end;
end;

// and here is reading it back out

for I := 0 to PizzaList.Count-1 do
begin
Memo2.Lines.Append('Name: ' + TTuple<String, String, String, String>(PizzaList.Objects[I]).Value1);
Memo2.Lines.Append('Topping1: ' + TTuple<String, String, String, String>(PizzaList.Objects[I]).Value2);
Memo2.Lines.Append('Topping2: ' + TTuple<String, String, String, String>(PizzaList.Objects[I]).Value3);
Memo2.Lines.Append('Topping3: ' + TTuple<String, String, String, String>(PizzaList.Objects[I]).Value4);
end;
And finally here is the XSuperObject into a TStringList. For me this seems like the most dynamic way. There are no predefined names hard coded into your code and it supports an unlimited number of name value pairs. However, it does only support string types and probably takes up some more memory than some of the other ways:
procedure TForm1.LoadJSONStringLists(S: String);
var
aobj: ISuperArray;
obj, obj2: ISuperObject;
I, II: Integer;
Pizza: TStringList;
begin

aobj := SA(S);
for I := 0 to aobj.Length-1 do
begin
obj2 := aobj.O[I];

Pizza := TStringList.Create;
for II := 0 to obj2.Count-1 do
begin
Pizza.Append(obj2.CurrentKey+'='+obj2.CurrentValue.Value);
obj2.Next;
end;
PizzaList.AddObject(Pizza.Values['Name'], Pizza);
end;
end;

// and here is reading it back out

for I := 0 to PizzaList.Count-1 do
begin
SL := TStringList(PizzaList.Objects[I]);
for II := 0 to SL.Count-1 do
begin
Memo2.Lines.Append(SL.Names[II]+': ' + TStrings(PizzaList.Objects[I]).Values[SL.Names[II]]);
end;
end;
Download the full source code for the four different ways to parse JSON with Delphi XE6 Firemonkey.

Exit mobile version