Google Gson 使用詳解
Gson Summary
Java 解析 Json 最常用的類庫有:google 的 Gson、阿里巴巴的 FastJson、以及 Jackson。這些都是非常優秀而且常用的庫。
GSON 是 Google提供的用來在 Java 物件和 JSON 資料之間進行對映的 Java 類庫,可以快速的將一個 Json 字元轉成一個 Java 物件,或者將一個
gson 在 github 上開源地址:https://github.com/google/gson
二進位制開發包下載
所有版本下載地址: gson 二進位制開發包下載地址:https://search.maven.org/artifact/com.google.code.gson/gson/2.8.5/jar
gson-2.8.4.jar下載、gson-2.8.5.jar下載
Maven 依賴
gson 在 Maven 倉庫地址:https://mvnrepository.com/artifact/com.google.code.gson/gson
<!-- https://mvnrepository.com/artifact/com.google.code.gson/gson -->
<dependency>
<groupId>com.google.code.gson</groupId>
<artifactId>gson</artifactId>
<version>2.8.5</version>
</dependency>
<!-- https://mvnrepository.com/artifact/com.google.code.gson/gson -->
<dependency>
<groupId>com.google.code.gson</groupId>
<artifactId>gson</artifactId>
<version>2.8.4</version>
</dependency>
編碼示例
Gson toJson 與 fromJson
Gson 提供了 fromJson() 和 toJson() 兩個直接用於解析和生成的方法,前者實現反序列化,後者實現了序列化。同時每個方法都提供了過載方法.。
Gson 物件的 toJson 方法可以將基本資料型別、以及 POJO 物件、List、Map 等轉為 json 格式的字串
Gson 物件的 fromJson 方法做與 toJson 相反的操作,將 json 格式的字串轉為基本資料型別、 POJO 物件、List、Map 等
package com.lct.other;
import com.google.gson.Gson;
import com.google.gson.reflect.TypeToken;
import com.lct.domain.Person;
import java.text.SimpleDateFormat;
import java.util.ArrayList;
import java.util.Date;
import java.util.List;
/**
* Created by Administrator on 2018/11/23 0023.
*/
public class GsonUtils {
/**
* json 字串 -> 轉為基本資料型別
*/
public static void parserJsonToBasicData() {
Gson gson = new Gson();
/**
* <T> T fromJson(String json, Class<T> classOfT)
* json:被解析的 json 字串
* classOfT:解析結果的型別,可以是基本型別,也可以是 POJO 物件型別
*/
int i = gson.fromJson("100", int.class);
double d = gson.fromJson("100.99", Double.class);
boolean b = gson.fromJson("true", boolean.class);
String s = gson.fromJson("愛你", String.class);
System.out.print(i + "\t" + d + "\t" + b + "\t" + s);
//輸出:100 100.99 true 愛你
}
/**
* 基本型別 -> 轉為 Json 字串
*/
public static void parserBasicDataToJson() {
Gson gson = new Gson();
/**
* String toJson(Object src)
* 將物件轉為 json,如 基本資料、POJO 物件、以及 Map、List 等
*/
String jsonNumber = gson.toJson(100);
String jsonDouble = gson.toJson(100.99);
String jsonBoolean = gson.toJson(false);
String jsonString = gson.toJson("Tiger");
System.out.println(jsonNumber + "\t" + jsonDouble + "\t" + jsonBoolean + "\t" + jsonString);
//輸出:100 100.99 false "Tiger"
}
/**
* 陣列格式的 Json 字串 - > 轉為 陣列
*/
public static void parserJsonStrToArray() {
String jsonArrayStr = "[\"Java\",\"Android\",\"IOS\"]";
Gson gson = new Gson();
String[] strings = gson.fromJson(jsonArrayStr, String[].class);
for (int i = 0; i < strings.length; i++) {
System.out.print((i + 1) + ":" + strings[i] + "\t");
}
//輸出:1:Java 2:Android 3:IOS
}
/**
* 陣列格式的 Json 字串 - > 轉為 List 列表
*/
public static void parserJsonStrToList() {
String jsonArray = "[\"Java1\",\"Android2\",\"IOS3\"]";
Gson gson = new Gson();
/**
* 如果解析結果是普通物件,如 單純的 POJO,則可以使用 fromJson(String json, Class<T> classOfT)
* 如果解析結果是複雜型別,如 List<T> 這種,則應該使用 fromJson(String json, Type typeOfT)
* json:被轉換的 json 格式的字串
* typeOfT:解析結果型別
*/
List<String> stringList = gson.fromJson(jsonArray, new TypeToken<List<String>>() {
}.getType());
for (int i = 0; i < stringList.size(); i++) {
System.out.print((i + 1) + ":" + stringList.get(i) + "\t");
}
//輸出:1:Java1 2:Android2 3:IOS3
}
/**
* Java POJO 物件 -> 轉為 json 字串
*/
public static void parserPOJOToJson() {
Person person = new Person();
person.setpId(9527);
person.setpName("華安");
person.setBirthday(new Date());
person.setIsMarry(true);
Gson gson = new Gson();
/**
* String toJson(Object src)
* 將物件轉為 json,如 基本資料、POJO 物件、以及 Map、List 等
* 注意:如果 POJO 物件某個屬性的值為 null,則 toJson(Object src) 預設不會對它進行轉化
* 結果字串中不會出現此屬性
*/
String jsonUser = gson.toJson(person);
System.out.println(jsonUser);
//輸出:{"pId":9527,"pName":"華安","birthday":"Nov 23, 2018 1:50:56 PM","isMarry":true}
}
/**
* Json 字串 -> 轉為 POJO 物件
*/
public static void parserJsonToPOJO() {
/**符合 json 格式的字串*/
String personJson = "{\"pId\":9527,\"pName\":\"華安\",\"birthday\":\"Nov 23, 2018 1:50:56 PM\",\"isMarry\":true}";
Gson gson = new Gson();
/**
* <T> T fromJson(String json, Class<T> classOfT)
* json:被解析的 json 字串
* classOfT:解析結果的型別,可以是基本型別,也可以是 POJO 物件型別,gson 會自動轉換
*/
Person person = gson.fromJson(personJson, Person.class);
System.out.println(person);
//輸出:Person{birthday=Fri Nov 23 13:50:56 CST 2018, pId=null, pName='華安', isMarry=true}
SimpleDateFormat dateFormat = new SimpleDateFormat("yyyy-MM-dd HH:mm:ss");
String personBirthday = dateFormat.format(person.getBirthday());
System.out.println("使用者生日:" + personBirthday);
//輸出:使用者生日:2018-11-23 13:50:56
//可見日期字串也能完美轉換
}
/**
* List 集合 -> 轉為 json 字串
* list 會被解析成 Json 陣列,List 中的元素被解析成 json
*/
public static void parserPOJOListToJson() {
Person person = new Person();
person.setpId(9527);
person.setpName("華安");
person.setBirthday(new Date());
person.setIsMarry(true);
Person person2 = new Person();
person2.setpId(8866);
person2.setpName("寧王");
List<Person> personList = new ArrayList<>();
personList.add(person);
personList.add(person2);
Gson gson = new Gson();
/**
* String toJson(Object src)
* 將物件轉為 json,如 基本資料、POJO 物件、以及 Map、List 等
* 注意:如果 POJO 物件某個屬性的值為 null,則 toJson(Object src) 預設不會對它進行轉化
* 結果字串中不會出現此屬性
*/
String personListJson = gson.toJson(personList);
System.out.println(personListJson);
//輸出:[{"pId":9527,"pName":"華安","birthday":"Nov 23, 2018 2:05:58 PM","isMarry":true},{"pId":8866,"pName":"寧王","isMarry":false}]
}
}
JsonObject、JsonArray、JsonParser
JsonObject 表示 json 物件、JsonArray 表示 json 物件陣列、JsonParser 表示 json 解析,將 json 格式的字串解析為 JsonObject、JsonArray 物件。
package com.lct.other;
import com.google.gson.JsonArray;
import com.google.gson.JsonObject;
import com.google.gson.JsonParser;
/**
* Created by Administrator on 2018/11/23 0023.
*/
public class JsonUtils {
/**
* Json 格式字串 -> 解析為 JSON 物件
*/
public static void parserJsonStrToJsonObj() {
String jsonStr = "{\"pId\":9527,\"pName\":\"華安\",\"birthday\":\"Nov 23, 2018 1:50:56 PM\",\"isMarry\":true}";
JsonParser jsonParser = new JsonParser();
/**JsonElement parse(String json)
* 如果被解析的字串不符合 json 格式,則丟擲異常*/
JsonObject jsonObject = jsonParser.parse(jsonStr).getAsJsonObject();
/**JsonElement get(String memberName)
* 注意:如果 get 的 key 不存在,則返回 null,如果不加判斷而進行取值的話,會拋:java.lang.NullPointerException
* */
Integer pId = jsonObject.get("pId").getAsInt();
String pName = jsonObject.get("pName").getAsString();
System.out.println(jsonObject);
//輸出:{"pId":9527,"pName":"華安","birthday":"Nov 23, 2018 1:50:56 PM","isMarry":true}
System.out.println(pId + "\t" + pName);
//輸出:9527 華安
}
/**
* Json 陣列字串 -> 解析為 JSON 陣列物件
*/
public static void parserJsonStrToJsonArray() {
String jsonArrayStr = "[{\"pId\":9527,\"pName\":\"華安\",\"isMarry\":true},{\"pId\":8866,\"pName\":\"寧王\",\"isMarry\":false}]";
JsonParser jsonParser = new JsonParser();
JsonArray jsonArray = jsonParser.parse(jsonArrayStr).getAsJsonArray();
for (int i = 0; i < jsonArray.size(); i++) {
JsonObject jsonObject = jsonArray.get(i).getAsJsonObject();
System.out.println((i + 1) + ":" + jsonObject + "\t\t" + jsonObject.get("pName").getAsString());
}
//輸出:1:{"pId":9527,"pName":"華安","isMarry":true} 華安
//輸出:2:{"pId":8866,"pName":"寧王","isMarry":false} 寧王
}
/**
* 手動 建立 JSON物件 並新增基本型別屬性
*/
public static void createJsonObj() {
/**
* JsonObject 新增基本型別屬性使用 addProperty(String property, Number value)、 addProperty(String property, String value) 等
* JsonObject 新增複雜型別屬性使用 add(String property, JsonElement value)
* JsonObject 與 JsonArray 都是 JsonElement 類的子類
* 提示:如果新增的 key 已經存在,則後面的會覆蓋前面的
*/
JsonObject jsonObject = new JsonObject();
jsonObject.addProperty("pId", 9527);
jsonObject.addProperty("pName", "華安");
jsonObject.addProperty("isMarry", true);
/**
* JsonObject 取值使用 JsonElement get(String memberName),根據 JsonElement 可以獲取任意型別
* JsonObject 可以直接獲取 JsonArray:JsonArray getAsJsonArray(String memberName)
* JsonObject 可以直接獲取 JsonObject:JsonObject getAsJsonObject(String memberName)
*/
System.out.println(jsonObject + "\t" + jsonObject.get("pName").getAsString());
//輸出:{"pId":9527,"pName":"華安","isMarry":true} 華安
}
/**
* 建立 JSON 陣列
*/
public static void createJsonArray() {
String json1 = "{\"pId\":9527,\"pName\":\"華安\",\"isMarry\":true}";
String json2 = "{\"pId\":1200,\"pName\":\"安祿山\",\"isMarry\":false}";
JsonObject jsonObject1 = new JsonParser().parse(json1).getAsJsonObject();
JsonObject jsonObject2 = new JsonParser().parse(json2).getAsJsonObject();
JsonArray jsonArray = new JsonArray();
jsonArray.add(jsonObject1);
jsonArray.add(jsonObject2);
System.out.println(jsonArray);
//輸出:[{"pId":9527,"pName":"華安","isMarry":true},{"pId":1200,"pName":"安祿山","isMarry":false}]
}
/**
* 刪除 JsonObject 的某個屬性
*/
public static void delJsonObjproperty() {
String json = "{\"pId\":9527,\"pName\":\"華安\",\"isMarry\":true}";
JsonObject jsonObject = new JsonParser().parse(json).getAsJsonObject();
System.out.println("刪除前:" + jsonObject);
//輸出:刪除前:{"pId":9527,"pName":"華安","isMarry":true}
/**
* JsonElement remove(String property)
* 用於刪除 JsonObject 的屬性,返回被刪除的屬性的值,原 JsonObject 會改變
* 與get取值同理,如果 remove 的屬性值不存在,則返回 null
*/
String delProperty = jsonObject.remove("pName").getAsString();
System.out.println("刪除 " + delProperty + " 後:" + jsonObject);
//輸出:刪除 華安 後:{"pId":9527,"isMarry":true}
}
/**
* 修改 JsonObject 屬性,與新增一樣使用 addProperty,當 key 已經存在時,會覆蓋舊值
*/
public static void updateJsonObjproperty() {
String json = "{\"currentOnlineNumber\":\"101\",\"name\":\"汪茂雄\"}";
JsonObject jsonObject = new JsonParser().parse(json).getAsJsonObject();
System.out.println("修改前:" + jsonObject);
jsonObject.addProperty("name", "趙麗穎");
System.out.println("修改後:" + jsonObject);
}
/**
* 獲取 JsonObject 屬性值
*/
public static void getJsonObjproperty() {
String json = "{\"pId\":9527,\"pName\":\"華安\",\"Dog\":{\"dName\":\"小黃\",\"color\":\"yellow\"}}";
JsonObject jsonObject = new JsonParser().parse(json).getAsJsonObject();
System.out.println("操作物件:" + jsonObject);
/**
* JsonElement get(String memberName):如果 memberName 不存在,則返回 null
* 所以除非應用中明確知道key存在,否則應該加以判斷
*/
Integer pId = jsonObject.get("pId").getAsInt();
System.out.println("pId=" + pId);
/** boolean has(String memberName)
* 判斷 JsonObject 中是否存在某個 key*/
if (!jsonObject.has("name")) {
System.out.println("name 屬性不存在...");
}
/**
* JsonObject 取值使用 JsonElement get(String memberName),根據 JsonElement 可以獲取任意型別
* JsonObject 可以直接獲取 JsonArray:JsonArray getAsJsonArray(String memberName)
* JsonObject 可以直接獲取 JsonObject:JsonObject getAsJsonObject(String memberName)
*/
JsonObject dogJson = jsonObject.getAsJsonObject("Dog");
System.out.println(dogJson);
}
/**
* 實際應用中,如果業務比較複雜,則通常都會巢狀 json,如下所示:
* [{"pId":110,"pName":"華安","Dog":{"dName":"小黃","color":"yellow"}},{"pId":120,"pName":"安祿山","Dog":{"dName":"阿毛","color":"red"}}]
*/
public static void complexParsen() {
/**兩隻小狗 json 字串*/
String dog1JsonStr = "{\"dName\":\"小黃\",\"color\":\"yellow\"}";
String dog2JsonStr = "{\"dName\":\"阿毛\",\"color\":\"red\"}";
/**將 json 字串解析為 JsonObject 物件*/
JsonObject dog1Json = new JsonParser().parse(dog1JsonStr).getAsJsonObject();
JsonObject dog2Json = new JsonParser().parse(dog2JsonStr).getAsJsonObject();
/**建立兩個使用者的 JsonObject 物件*/
JsonObject user1Json = new JsonObject();
JsonObject user2Json = new JsonObject();
/**新增普通值*/
user1Json.addProperty("pId", 110);
user1Json.addProperty("pName", "華安");
/**新增JsonObject物件
* 注意:新增的物件,而不應該是符合 json 格式的字串*/
user1Json.add("Dog", dog1Json);
user2Json.addProperty("pId", 120);
user2Json.addProperty("pName", "阿毛");
user2Json.add("Dog", dog2Json);
/**建立 JsonArray 用於存放 JsonObject
* 同樣新增的應該是物件,而不應該是符合格式的字串*/
JsonArray jsonArray = new JsonArray();
jsonArray.add(user1Json);
jsonArray.add(user2Json);
System.out.println(jsonArray);
//輸出:[{"pId":110,"pName":"華安","Dog":{"dName":"小黃","color":"yellow"}},{"pId":120,"pName":"阿毛","Dog":{"dName":"阿毛","color":"red"}}]
}
public static void main(String[] args) {
getJsonObjproperty();
}
}
欄位值為 null 時是否序列化
Gson 在 toJson 的時候,預設是不會對屬性值為 null 的欄位進行序列化的,即結果中不會包含它,可以使用 GsonBuild 的 serializeNulls 方法構建 Gson,這樣就會對屬性值為 null 的欄位進行序列化。
實際應用中,是否對屬性值為 null 的欄位進行序列化,根據需求定即可,建議進行序列化。
/**
* 物件中為 null 的欄位,是否實行序列化,為了降低 bug,應該保持一致
* 實際應用中,前後臺數據互動,系統之間資料傳遞時,如果接收端在獲取某個值的時候不存在,而傳送端以為自己以及傳送了,
* 其實就是欄位值可能為 null,傳送端傳送的時候,導致沒有進行序列化
*/
public static void parserPOJOToJsonContainNull() {
/**
* Person 實體一共4個欄位:Integer pId、String pName、Date birthday、Boolean isMarry
* 現在它的屬性全部不進行賦值
*/
Person person = new Person();
/** 不對屬性值為 null 的欄位進行序列化,轉換結果會為空*/
String personStr = new Gson().toJson(person);
/** 對屬性值為 null 的欄位進行序列化*/
String personStrFinal = new GsonBuilder().serializeNulls().create().toJson(person);
System.out.println(personStr);
//輸出:{}
System.out.println(personStrFinal);
//輸出:{"pId":null,"pName":null,"birthday":null,"isMarry":null}
/** 對於欄位值為 null 的字串,解析的時候也需要注意
* JsonElement get(String memberName) 的時候返回的就是 null
*/
JsonObject jsonObject = new JsonParser().parse(personStrFinal).getAsJsonObject();
System.out.println(jsonObject.get("pName"));//輸出:null
/**判斷元素是否為 null*/
System.out.println(jsonObject.get("pName").isJsonNull());
//輸出:true
}