知識庫 / JSON RSS 訂閱

使用Gson比較兩個JSON對象

JSON
HongKong
6
09:52 PM · Dec 05 ,2025

1. 概述

JSON 是一種數據的字符串表示形式。我們可能需要在算法或測試中比較這些數據。儘管可以比較包含 JSON 的字符串,但 字符串比較對錶示形式敏感,而不是內容本身

為了克服這一點並以語義方式比較 JSON 數據,我們需要將數據加載到內存中的一個結構中,該結構不受空格或對象鍵順序等因素的影響。

在本簡短教程中,我們將使用 Gson,一個 JSON 序列化/反序列化庫,它可以對 JSON 對象進行深度比較。

2. 不同字符串中具有語義相同 JSON 數據

讓我們更深入地瞭解我們試圖解決的問題。

假設我們有兩個字符串,它們都代表相同 JSON 數據,但其中一個字符串末尾有額外的空格:

String string1 = "{\"fullName\": \"Emily Jenkins\", \"age\": 27    }";
String string2 = "{\"fullName\": \"Emily Jenkins\", \"age\": 27}";

雖然 JSON 對象的內容相等,但將它們作為字符串進行比較會顯示出差異:

assertNotEquals(string1, string2);

如果對象中鍵的順序有所不同,同樣會發生同樣的情況,儘管 JSON 通常對這一點不敏感:

String string1 = "{\"fullName\": \"Emily Jenkins\", \"age\": 27}";
String string2 = "{\"age\": 27, \"fullName\": \"Emily Jenkins\"}";
assertNotEquals(string1, string2);

因此,使用 JSON 處理庫來比較 JSON 數據將會有所裨益。

3. Maven 依賴

要使用 Gson,首先添加 Gson Maven 依賴:

<dependency>
    <groupId>com.google.code.gson</groupId>
    <artifactId>gson</artifactId>
    <version>2.11.0</version>
</dependency>

4. 將 JSON 解析為 Gson 對象

在深入比較對象之前,讓我們先看看 Gson 如何在 Java 中表示 JSON 數據。

在 Java 中處理 JSON 時,我們首先需要將 JSON 字符串轉換為 Java 對象。Gson 提供 JsonParser,它將源 JSON 解析為 JsonElement 樹:

String objectString = "{\"customer\": {\"fullName\": \"Emily Jenkins\", \"age\": 27 }}";
String arrayString = "[10, 20, 30]";

JsonElement json1 = JsonParser.parseString(objectString);
JsonElement json2 = JsonParser.parseString(arrayString);

JsonElement 是一個抽象類,代表 JSON 中的一個元素。parse 方法返回一個JsonElement 的實現,該實現可以是JsonObjectJsonArrayJsonPrimitiveJsonNull

assertTrue(json1.isJsonObject());
assertTrue(json2.isJsonArray());

那些子類(如 JsonObjectJsonArray 等)覆蓋了 Object.equals 方法,從而提供了一種有效的深層 JSON 比較。

5. Gson 比較使用案例

Gson 提供了多種使用場景,以下是一些常見的比較案例:

  • JSON 到 Java 對象轉換: Gson 最常見的用途是將 JSON 字符串解析為 Java 對象。例如,從 API 獲取數據並將其轉換為 Java Bean 對象進行處理。
  • Java 對象到 JSON 轉換: Gson 同樣可以用於將 Java 對象序列化為 JSON 字符串,方便在不同的系統之間進行數據交換。
  • 自定義序列化和反序列化: Gson 允許您自定義序列化和反序列化過程,例如,可以定義自定義的字段轉換器來處理特定類型的字段。
  • 處理嵌套 JSON 結構: Gson 可以輕鬆處理嵌套的 JSON 結構,例如,可以遞歸地將 JSON 字符串解析為嵌套的 Java 對象。
  • 處理數組和列表: Gson 可以處理 JSON 數組和列表,並將其轉換為 Java 數組和列表。
  • 處理日期和時間: Gson 提供了對日期和時間的支持,可以將其轉換為 Java Date 對象,或將其轉換為 JSON 格式的日期字符串。
  • 處理枚舉類型: Gson 可以處理枚舉類型,並將其轉換為 JSON 格式的字符串,或將其轉換為 Java 枚舉類型。
  • 處理 null 值: Gson 提供了對 null 值的處理機制,可以將其轉換為 JSON 格式的 null 值,或將其轉換為 Java null 值。

5.1. 比較兩個簡單的JSON對象

假設我們有兩個字符串,分別代表簡單的JSON對象,其中鍵的順序不同:

第一個對象中,fullNameage 之前:

{
    "customer": {
        "id": 44521,
        "fullName": "Emily Jenkins",
        "age": 27
    }
}

第二個反轉順序:

{
    "customer": {
        "id": 44521,
        "age": 27,
        "fullName": "Emily Jenkins"
    }
}

我們只需解析並比較它們:

assertEquals(parser.parse(string1), parser.parse(string2));

在這種情況下,JsonParser 返回一個 JsonObject,其 equals 實現不具有 順序敏感性

5.2. 比較兩個 JSON 數組

在 JSON 數組的情況下,JsonParser 將返回一個 JsonArray

如果數組在一個特定順序中:

[10, 20, 30]
assertTrue(JsonParser.parseString(string1).isJsonArray());

我們可以將其與另一個進行比較,順序可以不同:

[20, 10, 30]

JsonObject 相比,JsonArrayequals 方法是順序敏感的,因此這些數組不相等,這在語義上是正確的:

assertNotEquals(JsonParser.parseString(string1), JsonParser.parseString(string2));

5.3. 比較兩個嵌套的 JSON 對象

正如我們之前所見,<em JsonParser </em> 可以解析 JSON 的樹狀結構。每個 <em JsonObject </em><em JsonArray </em>> 都包含其他的 <em JsonElement </em> 對象,這些對象本身可以是 <em JsonObject </em><em JsonArray </em> 類型。

當我們使用 equals 方法時,它會遞歸地比較所有成員,這意味着嵌套對象也會被比較:

如果這是 <em string1 </em>>

{
  "customer": {
    "id": "44521",
    "fullName": "Emily Jenkins",
    "age": 27,
    "consumption_info": {
      "fav_product": "Coke",
      "last_buy": "2012-04-23"
    }
  }
}

以下JSON字符串是string2:

{
  "customer": {
    "fullName": "Emily Jenkins",
    "id": "44521",
    "age": 27,
    "consumption_info": {
      "last_buy": "2012-04-23",
      "fav_product": "Coke"
   }
  }
}

然後我們仍然可以使用 equals 方法來比較它們:

assertEquals(JsonParser.parseString(string1), JsonParser.parseString(string2));

6. 結論

在本文中,我們探討了將 JSON 作為 String 進行比較的挑戰。我們看到了 Gson 如何允許我們解析這些字符串,將其轉換為支持比較的對象結構。

發佈 評論

Some HTML is okay.