首頁 >後端開發 >Golang >如何在沒有通用佔位符字段的情況下在 Go 中解組動態 JSON?

如何在沒有通用佔位符字段的情況下在 Go 中解組動態 JSON?

Patricia Arquette
Patricia Arquette原創
2024-12-12 11:39:12946瀏覽

How to Unmarshal Dynamic JSON in Go without Generic Placeholder Fields?

基於類型鍵解組動態 JSON

簡介

將 JSON 資料解組到 Go 結構中可能是一項簡單的任務。但是,在處理包含動態資料結構的 JSON 文件時,欄位的類型可能會有所不同,因此該過程可能會變得更加複雜。本文探討了解決此挑戰的方法,而不引入通用佔位符欄位。

問題定義

考慮以下JSON 規格:

{
  "some_data": "foo",
  "dynamic_field": { "type": "A", "name": "Johnny" },
  "other_data": "bar"
}
{
  "some_data": "foo",
  "dynamic_field": { "type": "B", "address": "Somewhere" },
  "other_data": "bar"
}

兩個JSON 文件都應該被解組到同一個Go 結構中:

type BigStruct struct {
  SomeData     string    `json:"some_data"`
  DynamicField Something `json:"dynamic_field"`
  OtherData    string    `json:"other_data"`
}

關鍵問題是:如何建立Something 類型並實現解組邏輯?

解決方案:使用自訂UnmarshalJSON 方法的介面

解決方案涉及為Something 類型建立介面:

type Something interface {
  GetType() string
}

接下來,定義實作Something 介面的特定結構類型:

type BaseDynamicType struct {
  Type string `json:"type"`
}

type DynamicTypeA struct {
  BaseDynamicType
  Name string `json:"name"`
}

type DynamicTypeB struct {
  BaseDynamicType
  Address string `json:"address"`
}

The DynamicType 介面方法允許將JSON資料解組為適當的結構:

func (d *DynamicType) UnmarshalJSON(data []byte) error {
    var typ struct {
        Type string `json:"type"`
    }
    if err := json.Unmarshal(data, &typ); err != nil {
        return err
    }
    switch typ.Type {
    case "A":
        d.Value = new(TypeA)
    case "B":
        d.Value = new(TypeB)
    }
    return json.Unmarshal(data, d.Value)
}

此方法檢查 JSON 資料並根據需要建立 TypeA 或 TypeB 的實例。

在上實作UnmarshalJSON BigStruct

最後,在BigStruct 上實作UnmarshalJSON 方法type:

func (b *BigStruct) UnmarshalJSON(data []byte) error {
    var tmp BigStruct // avoids infinite recursion
    return json.Unmarshal(data, &tmp)
}

此方法使用臨時來避免「資料中的類型欄位使用適當的DynamicType 類型對動態欄位進行解組。

結論

該解決方案提供了一種乾淨有效的方法來解組動態 JSON 數據,而不需要額外的通用佔位符字段。透過使用介面並實作自訂 UnmarshalJSON 方法,Go 結構體可以適應 JSON 輸入中的動態資料結構。

以上是如何在沒有通用佔位符字段的情況下在 Go 中解組動態 JSON?的詳細內容。更多資訊請關注PHP中文網其他相關文章!

陳述:
本文內容由網友自願投稿,版權歸原作者所有。本站不承擔相應的法律責任。如發現涉嫌抄襲或侵權的內容,請聯絡admin@php.cn