Xe7 System.Json解析數據格式,xe7system.json
一、Demo一 解析嵌套數組
Json數據

![]()
{"code":1,"msg":"","data":{"GradeInfo":[{"gradeid":1,"gradename":"普通介紹人","graderate":0.02}],"UserList":[{"stype":"User","userid":"119110"},{"stype":"User","userid":"11911044"},{"stype":"User","userid":"119110444"},{"stype":"User","userid":"121121"},
{"stype":"User","userid":"13211111113"},{"stype":"User","userid":"abcadsfa"},{"stype":"Customer","userid":"admin"},{"stype":"Shoper","userid":"Shop2222"}]}}
View Code

![]()
var
Jsobj:TJSONObject;
i,j:Integer;
Jarr:TJSONArray;
temp:string;
v:string;
Jsvalue:Tjsonvalue ;
begin
Jsobj:=TJSONObject.ParseJSONValue(Memo1.Text) as TJSONObject;
temp:=Jsobj.GetValue('data').ToString;
Jsobj:=TJSONObject.ParseJSONValue(temp) as TJSONObject;
jarr := TJSONArray(Jsobj.GetValue('UserList'));
for i := 0 to Jarr.Size-1 do
begin
v:=(Jarr.Items[i].ToString);
Jsobj:=TJSONObject.ParseJSONValue(v) as TJSONObject;
// for j := 0 to Jsobj.Count do
// begin
ShowMessage(Jsobj.GetValue('userid').ToString);
//end;
end;
end;
View Code
二 Demo二
Delphi XE5帶了system.json單元,原生提供了json支持類。下面是解析json用法說明:
最簡單的JSON大致像這樣
{
"date":"周二(今天, 實時:12℃)",
"dayPictureUrl":"http://api.map.baidu.com/images/weather/day/duoyun.png",
"nightPictureUrl":"http://api.map.baidu.com/images/weather/night/duoyun.png",
"weather":"多雲",
"wind":"北風微風",
"temperature":"15 ~ 6℃"
}
對於這種格式比較簡單的json,解析是非常容易的
StrJson := RESTResponse1.Content;
JSONObject := TJSONObject.ParseJSONValue(TEncoding.UTF8.GetBytes(StrJson), 0) as TJSONObject;
JSONObject.getValue('date');
就可以得到date的值。如果像下面的這樣結構比較復雜的json,就需要首先分析清楚這個json的格式才能獲取成功。
{
"error":0,
"status":"success",
"date":"2014-03-04",
"results":
[{"currentCity":"成都",
"weather_data":[
{
"date":"周二(今天, 實時:12℃)",
"dayPictureUrl":"http://api.map.baidu.com/images/weather/day/duoyun.png",
"nightPictureUrl":"http://api.map.baidu.com/images/weather/night/duoyun.png",
"weather":"多雲",
"wind":"北風微風",
"temperature":"15 ~ 6℃"
},
{
"date":"周三",
"dayPictureUrl":"http://api.map.baidu.com/images/weather/day/yin.png",
"nightPictureUrl":"http://api.map.baidu.com/images/weather/night/xiaoyu.png",
"weather":"陰轉小雨",
"wind":"北風微風",
"temperature":"14 ~ 7℃"
},
{
"date":"周四",
"dayPictureUrl":"http://api.map.baidu.com/images/weather/day/xiaoyu.png",
"nightPictureUrl":"http://api.map.baidu.com/images/weather/night/xiaoyu.png",
"weather":"小雨",
"wind":"北風微風",
"temperature":"12 ~ 7℃"
},
{
"date":"周五",
"dayPictureUrl":"http://api.map.baidu.com/images/weather/day/xiaoyu.png",
"nightPictureUrl":"http://api.map.baidu.com/images/weather/night/xiaoyu.png",
"weather":"小雨",
"wind":"南風微風",
"temperature":"9 ~ 6℃"
}
]
}
]}
這是一個嵌套結構,最外層是一個記錄,包含"error", "status", "date", "results"四個字段,前三個都是簡單的鍵值對,而“results”是一個數組,目前只有一個元素,即一條記錄,這條記錄的字段是"currentCity"和"weather_data",再進一步"weather_data"又是一個組數,它有4個元素或者記錄,每條記錄裡包含 "date", "dayPictureUrl","nightPictureUrl", "weather","wind", "temperature"字段。
要想取出裡面的"weather_data",利用目前的DBXJSON裡的TJSONObject是不能直接取出來的,例如這樣
StrJson := RESTResponse1.Content;
JSONObject := TJSONObject.ParseJSONValue(TEncoding.UTF8.GetBytes(StrJson), 0)
as TJSONObject;
weather := JSONObject.GetValue('weather_data');
需要一步一步的走,由於最外面是一個簡單的json,可以先取出results,然後再取weather_data。
var
JSONObject: TJSONObject;
LItem: TJSONValue;
LJPair: TJSONPair;
weather: TJSONArray;
StrJson: String;
result: String;
i: Integer;
begin
StrJson := 'xxxxxxx';//假定是上面那個json
JSONObject := TJSONObject.ParseJSONValue(TEncoding.UTF8.GetBytes(StrJson), 0)
as TJSONObject;
JSONObject := (JSONObject.GetValue('results') as TJSONArray).Get(0)
as TJSONObject;
weather := JSONObject.GetValue('weather_data') as TJSONArray;
for i := 0 to weather.size - 1 do //應該是4條記錄
begin
LItem := (weather.Get(i) as TJSONObject).GetValue('weather'); //得到weather的值
result := result '|' LItem.Value;
end;
end
這段代碼只是為了說明使用方法,沒有做類型檢查,最好在進行類型轉換之前用is TJSONArray先判斷是不是數組。
原文地址
補充,在原文中,作者沒有提到,如何檢查一個指定的串值是否存在,比如下面這行代碼:
weather := JSONObject.GetValue('weather_data');
如果'weather_data'不存在,JSONObject.GetValue方法是要產生異常的,那麼,該如何檢查weath_data是否存在呢?
先聲明一個
var
jsonvalue: Tjsonvalue;
然後,利用JSONObject.TryGetValue方法來檢查。
if jsonObject.TryGetValue('weather_data', jsonvalue) then
...
如果weath_data存在,可以進一步通過jsonvalue.value取出其值。
注意,這個jsonvalue不用建立與釋放。
2014-11-19
網友發現上文中可能遇到的json串碼問題,並給出了解決代碼,Delphi <wbr>XE6 <wbr>原生解析jsonDelphi <wbr>XE6 <wbr>原生解析json!
procedure TForm1.Button2Click(Sender: TObject);
var
LJsonArr : TJSONArray;
LJsonValue : TJSONValue;
LItem : TJSONValue;
StrJson,S :string;
begin
StrJson := RESTresponse1.Content;
LJsonArr := TJSONObject.ParseJSONValue(TEncoding.UTF8.GetBytes(StrJson),0) as TJSONArray;
for LJsonValue in LJsonArr do
begin
for LItem in TJSONArray(LJsonValue) do
S :=Format('%s : %s',[TJSONPair(LItem).JsonString.Value, TJSONPair(LItem).JsonValue.Value]);
end;
end;
三、Demo三
{
功能:DelphiXE7中使用JSON
------------------------------------------------------------------------------
說明:
1,使用Delphi自己帶的JSON(system.json)。
2,這僅僅是一個簡單例子,以後還會增加演示功能。
------------------------------------------------------------------------------
注意:
1,JSON類創建後,裡面所有元素不用管釋放,JSON類自己管理,千萬不要畫蛇添足啊!!!!!!
------------------------------------------------------------------------------
作者:孫玉良 QQ:14667479 Email:sunylat@163.com 修改時間:2014/11/23 00:13
------------------------------------------------------------------------------
開發工具:Delphi XE7
測試手機:華為榮耀X1
}
unit Unit1;
interface
uses
System.SysUtils, System.Types, System.UITypes, System.Classes,
System.Variants,
FMX.Types, FMX.Controls, FMX.Forms, FMX.Graphics, FMX.Dialogs, FMX.StdCtrls,
FMX.Layouts, FMX.Memo;
type
TForm1 = class(TForm)
Panel1: TPanel;
Memo1: TMemo;
Panel2: TPanel;
Button1: TButton;
Button2: TButton;
Memo2: TMemo;
Button3: TButton;
procedure Button1Click(Sender: TObject);
procedure Button2Click(Sender: TObject);
procedure FormCreate(Sender: TObject);
procedure Button3Click(Sender: TObject);
procedure FormResize(Sender: TObject);
private
{ Private declarations }
// 重新設置button按鈕
procedure ResetButton;
public
{ Public declarations }
end;
var
Form1: TForm1;
const
// 演示用的JSON
jsonString = '{"name":"張三", "other":["中國","程序員"]}';
implementation
{$R *.fmx}
uses
System.json; // Dephi自帶的JSON單元
procedure TForm1.Button1Click(Sender: TObject);
var
JSONObject: TJSONObject; // JSON類
i: Integer; // 循環變量
temp: string; // 臨時使用變量
jsonArray: TJSONArray; // JSON數組變量
begin
if Trim(Memo1.Text) = '' then
begin
ShowMessage('要解析數據不能為空!');
end
else
begin
JSONObject := nil;
try
{ 從字符串生成JSON }
JSONObject := TJSONObject.ParseJSONValue(Trim(Memo1.Text)) as TJSONObject;
if JSONObject.Count > 0 then
begin
{ 1,遍歷JSON數據 }
Memo2.Lines.Add('遍歷JSON數據:' + #13#10);
Memo2.Lines.Add('JSON數據數量:' + IntToStr(JSONObject.Count));
for i := 0 to JSONObject.Count - 1 do
begin
if i = 0 then
begin
temp := JSONObject.Get(i).ToString + #13#10;;
end
else
begin
temp := temp + JSONObject.Get(i).ToString + #13#10;
end;
end;
{ output the JSON to console as String }
Memo2.Lines.Add(temp);
Memo2.Lines.Add('------------------------------');
{ 2,按元素解析JSON數據 }
Memo2.Lines.Add('按元素解析JSON數據:' + #13#10);
temp := 'name = ' + JSONObject.Values['name'].ToString + #13#10;
Memo2.Lines.Add(temp);
// json數組
jsonArray := TJSONArray(JSONObject.GetValue('other'));;
if jsonArray.Count > 0 then
begin
// 得到JSON數組字符串
temp := 'other = ' + JSONObject.GetValue('other').ToString + #13#10;
// 循環取得JSON數組中每個元素
for i := 0 to jsonArray.Size - 1 do
begin
temp := temp + IntToStr(i + 1) + ' : ' + jsonArray.Items[i]
.Value + #13#10;
end;
end;
Memo2.Lines.Add(temp);
end
else
begin
temp := '沒有數據!';
Memo2.Lines.Add(temp);
end;
finally
JSONObject.Free;
end;
end;
end;
// 清空顯示數據
procedure TForm1.Button2Click(Sender: TObject);
begin
Memo1.Text := '';
Memo2.Text := '';
end;
// 設置要解析的JSON數據
procedure TForm1.Button3Click(Sender: TObject);
begin
Memo1.Text := jsonString;
end;
// 設置要解析的JSON數據
procedure TForm1.FormCreate(Sender: TObject);
begin
Memo1.Text := jsonString;
end;
procedure TForm1.FormResize(Sender: TObject);
begin
// 重新設置button按鈕
self.ResetButton;
end;
// 重新設置button按鈕
procedure TForm1.ResetButton;
var
buttonWidth: Integer;
begin
buttonWidth := self.Width div 3;
Button1.Width := buttonWidth;
Button2.Width := buttonWidth;
Button3.Width := buttonWidth;
end;
end.