欧美bbbwbbbw肥妇,免费乱码人妻系列日韩,一级黄片

golang中encoding/json包的實現(xiàn)

 更新時間:2025年07月02日 15:05:13   作者:草海桐  
Go語言通過encoding/json包提供了對JSON數(shù)據(jù)的強大支持,本文主要介紹了golang中encoding/json包的實現(xiàn),具有一定的參考價值,感興趣的可以了解一下

Go 語言通過 encoding/json 包提供了對 JSON 數(shù)據(jù)的強大支持,包括序列化、反序列化、自定義處理、數(shù)組處理、任意結(jié)構(gòu)解析以及流式處理等。

1. 基本使用

1.1 結(jié)構(gòu)體字段與 JSON 的映射

在 Go 中,結(jié)構(gòu)體的字段可以通過 json 標(biāo)簽(JSON Tag)與 JSON 字段進行映射。如果不指定 json 標(biāo)簽,默認使用結(jié)構(gòu)體字段名的蛇形命名(小寫)作為 JSON 字段名。

type P struct { // 未使用json標(biāo)簽,自動根據(jù)字段名稱進行綁定
    Name    string
    Age     int
    Address string
    Sex     string
    Time    time.Time
}

type Person struct {
    Name    string `json:"name"`
    Age     int    `json:"age"`
    Address string `json:"-"`
    Sex     string `json:"sex,omitempty"`
}
  • 結(jié)構(gòu)體 P:未定義 json 標(biāo)簽,序列化時會使用結(jié)構(gòu)體字段名作為 JSON 字段名。
  • 結(jié)構(gòu)體 Person
    • NameAge 使用 json 標(biāo)簽映射為 nameage。
    • Address 使用 - 標(biāo)簽,表示不會被序列化。
    • Sex 使用 omitempty,當(dāng)字段為空時不會被序列化。

1.2 序列化與反序列化

func main() {
    p1 := P{
        Name:    "Jon",
        Age:     20,
        Address: "beijing",
        Sex:     "男",
        Time:    time.Now(),
    }

    p2 := Person{
        Name:    "hon",
        Age:     20,
        Address: "beijing",
        Sex:     "",
    }

    // 編碼(序列化)
    json1, err := json.Marshal(p1)
    // 處理錯誤
    fmt.Println(string(json1))
    // 輸出示例: {"Name":"Jon","Age":20,"Address":"beijing","Sex":"男","Time":"..."}

    json2, err := json.Marshal(p2)
    // 處理錯誤
    fmt.Println(string(json2))
    // 輸出示例: {"name":"hon","age":20}

    // 解碼(反序列化)
    var p3 Person
    err = json.Unmarshal(json1, &p3)
    // 處理錯誤
    fmt.Printf("%+v\n", p3)
    // 輸出: {Name:Jon Age:20 Address: Sex:男}

    err = json.Unmarshal(json2, &p3)
    // 處理錯誤
    fmt.Printf("%+v\n", p3)
    // 輸出: {Name:hon Age:20 Address: Sex:}
}
  • json.Marshal:將 Go 結(jié)構(gòu)體序列化為 JSON 字符串。
  • json.Unmarshal:將 JSON 字符串反序列化為 Go 結(jié)構(gòu)體。

2. 自定義 JSON 序列化與反序列化

有時候,默認的序列化和反序列化方式無法滿足需求,這時可以通過實現(xiàn) MarshalJSONUnmarshalJSON 方法來自定義行為。

2.1 自定義類型示例

type Massachusetts struct {
    Name string
}

type P3 struct {
    Name    string
    Address *Massachusetts
}

// 自定義 MarshalJSON 方法
func (m *Massachusetts) MarshalJSON() ([]byte, error) {
    return json.Marshal(struct {
        State string `json:"state"`
    }{
        State: m.Name,
    })
}

func Customize() {
    address := Massachusetts{Name: "beijing"}
    p := P3{
        Name:    "jon",
        Address: &address,
    }

    // 編碼
    jsonBytes, err := json.Marshal(p)
    // 處理錯誤
    fmt.Println(string(jsonBytes))
    // 輸出: {"Name":"jon","Address":{"state":"beijing"}}
}
  • Massachusetts 結(jié)構(gòu)體通過自定義 MarshalJSON 方法,將 Name 字段序列化為 state 字段。

3. 處理 JSON 數(shù)組

Go 中的切片(Slice)和數(shù)組(Array)可以很方便地序列化為 JSON 數(shù)組,反向亦然。

3.1 JSON 數(shù)組示例

type P4 struct {
    Name string `json:"name"`
    Age  int    `json:"age"`
}

func JsonArray() {
    people := []P4{
        {Name: "p1", Age: 22},
        {Name: "p2", Age: 23},
    }

    jonsBytes, err := json.Marshal(people)
    // 處理錯誤
    fmt.Println(string(jonsBytes))
    // 輸出: [{"name":"p1","age":22},{"name":"p2","age":23}]
}
  • JsonArray 函數(shù)展示了如何將切片序列化為 JSON 數(shù)組,以及如何進行反序列化。

4. 解析任意結(jié)構(gòu)的 JSON 數(shù)據(jù)

在處理來自外部系統(tǒng)的 JSON 數(shù)據(jù)時,通常無法提前知道其具體結(jié)構(gòu)。Go 提供了 map[string]interface{}interface{} 來處理這種情況。

4.1 任意結(jié)構(gòu) JSON 示例

func JsonAny() {
    jsonString := `{
        "name":"p1",
        "Age":21,
        "email":"1.@qq.com"
    }`

    var m map[string]interface{}
    err := json.Unmarshal([]byte(jsonString), &m)
    // 處理錯誤
    fmt.Printf("%+v\n", m)
    // 輸出: map[Age:21 email:1.@qq.com name:p1]
}
  • JsonAny 函數(shù)展示了如何將任意結(jié)構(gòu)的 JSON 字符串解析為 map[string]interface{},方便后續(xù)操作。

5. 流式處理 JSON 數(shù)據(jù)

對于大型 JSON 數(shù)據(jù),逐行讀寫(流式處理)比一次性加載整個文件更加高效。Go 提供了 json.Decoderjson.Encoder 來處理流式 JSON 數(shù)據(jù)。

5.1 使用json.Decoder解碼流式 JSON

func JsonNewDecoder() {
    jsonData := `{"name":"John", "age":23}`
    reader := strings.NewReader(jsonData)
    decoder := json.NewDecoder(reader)

    var p P4
    if err := decoder.Decode(&p); err != nil {
        fmt.Println(err)
    }
    fmt.Printf("%+v\n", p)
    // 輸出: {Name:John Age:23}
}
  • JsonNewDecoder 函數(shù)展示了如何使用 json.Decoderio.Reader 中逐行讀取和解析 JSON 數(shù)據(jù)。

5.2 使用json.Encoder編碼流式 JSON

func JsonNewEncoder() {
    p := P4{Name: "p1", Age: 22}
    writer := &strings.Builder{}
    encoder := json.NewEncoder(writer)

    if err := encoder.Encode(&p); err != nil {
        fmt.Println(err)
    }
    fmt.Println(writer.String())
    // 輸出: {"name":"p1","age":22}
}
  • JsonNewEncoder 函數(shù)展示了如何使用 json.Encoder 將 Go 數(shù)據(jù)結(jié)構(gòu)流式寫入 io.Writer。

6. 時間類型的序列化與反序列化

在處理包含時間字段的 JSON 數(shù)據(jù)時,默認的序列化格式為 RFC3339。如果需要自定義時間格式,可以通過自定義類型實現(xiàn)。

6.1 自定義時間格式示例

type CustomTime time.Time

func (ct CustomTime) MarshalJSON() ([]byte, error) {
    return []byte(fmt.Sprintf("\"%s\"", time.Time(ct).Format("2006-01-02 15:04:05"))), nil
}

func (ct *CustomTime) UnmarshalJSON(b []byte) error {
    str := string(b)
    str = str[1 : len(str)-1] // 去除雙引號
    t, err := time.Parse("2006-01-02 15:04:05", str)
    if err != nil {
        return err
    }
    *ct = CustomTime(t)
    return nil
}

type P5 struct {
    Name      string     `json:"name"`
    CreatedAt CustomTime `json:"created_at"`
}

func CustomTimeExample() {
    p := P5{
        Name:      "jon",
        CreatedAt: CustomTime(time.Now()),
    }

    jsonBytes, err := json.Marshal(p)
    // 處理錯誤
    fmt.Println(string(jsonBytes))
    // 輸出: {"name":"jon","created_at":"2025-04-03 23:48:31"}

    var p2 P5
    err = json.Unmarshal(jsonBytes, &p2)
    // 處理錯誤
    fmt.Printf("%+v\n", p2)
    // 輸出: {Name:jon CreatedAt:2025-04-03 23:48:31 +0800 CST}
}
  • CustomTime 類型通過實現(xiàn)自定義的 MarshalJSONUnmarshalJSON 方法,定義了時間的序列化和反序列化格式。

總結(jié)

Go 語言的 encoding/json 包提供了靈活而強大的工具來處理 JSON 數(shù)據(jù)。無論是基本的序列化和反序列化,還是復(fù)雜的自定義行為、數(shù)組處理、任意結(jié)構(gòu)解析以及流式處理,encoding/json 都能很好地滿足需求。理解并掌握這些功能,有助于在開發(fā)中高效地處理各種 JSON 數(shù)據(jù)相關(guān)的任務(wù)。

到此這篇關(guān)于golang中encoding/json包的實現(xiàn)的文章就介紹到這了,更多相關(guān)golang encoding/json包內(nèi)容請搜索腳本之家以前的文章或繼續(xù)瀏覽下面的相關(guān)文章希望大家以后多多支持腳本之家!

相關(guān)文章

  • go語言的sql包原理與用法分析

    go語言的sql包原理與用法分析

    這篇文章主要介紹了go語言的sql包原理與用法,較為詳細的分析了Go語言里sql包的結(jié)構(gòu)、相關(guān)函數(shù)與使用方法,需要的朋友可以參考下
    2016-07-07
  • GOLang?IO接口與工具使用方法講解

    GOLang?IO接口與工具使用方法講解

    這篇文章主要介紹了GOLang?IO接口與工具使用方法,文中通過示例代碼介紹的非常詳細,對大家的學(xué)習(xí)或者工作具有一定的參考學(xué)習(xí)價值,需要的朋友們下面隨著小編來一起學(xué)習(xí)吧
    2023-03-03
  • golang語言中for循環(huán)語句用法實例

    golang語言中for循環(huán)語句用法實例

    這篇文章主要介紹了golang語言中for循環(huán)語句用法,實例分析了for循環(huán)遍歷的使用技巧,具有一定參考借鑒價值,需要的朋友可以參考下
    2015-01-01
  • golang?beego框架路由ORM增刪改查完整案例

    golang?beego框架路由ORM增刪改查完整案例

    這篇文章主要為大家介紹了golang?beego框架路由ORM增刪改查完整案例,有需要的朋友可以借鑒參考下,希望能夠有所幫助,祝大家多多進步早日升職加薪
    2022-04-04
  • 在 Golang 中實現(xiàn)一個簡單的Http中間件過程詳解

    在 Golang 中實現(xiàn)一個簡單的Http中間件過程詳解

    本文在go web中簡單的實現(xiàn)了中間件的機制,這樣帶來的好處也是顯而易見的,當(dāng)然社區(qū)也有一些成熟的 middleware 組件,包括 Gin 一些Web框架中也包含了 middleware 相關(guān)的功能,具體內(nèi)容詳情跟隨小編一起看看吧
    2021-07-07
  • Golang pipe在不同場景下遠程交互

    Golang pipe在不同場景下遠程交互

    這篇文章主要介紹了Golang pipe在不同場景下遠程交互,pipe實現(xiàn)從一個進程重定向至另一個進程,它是雙向數(shù)據(jù)通道,用于實現(xiàn)進行間通信
    2023-03-03
  • golang 執(zhí)行命令行的實現(xiàn)

    golang 執(zhí)行命令行的實現(xiàn)

    本文主要介紹了golang 執(zhí)行命令行的實現(xiàn),文中通過示例代碼介紹的非常詳細,對大家的學(xué)習(xí)或者工作具有一定的參考學(xué)習(xí)價值,需要的朋友們下面隨著小編來一起學(xué)習(xí)學(xué)習(xí)吧
    2022-08-08
  • 關(guān)于Golang變量初始化/類型推斷/短聲明的問題

    關(guān)于Golang變量初始化/類型推斷/短聲明的問題

    這篇文章主要介紹了關(guān)于Golang變量初始化/類型推斷/短聲明的問題,本文給大家介紹的非常詳細,對大家的學(xué)習(xí)或工作具有一定的參考借鑒價值,需要的朋友可以參考下
    2021-02-02
  • 詳解Go語言中Get/Post請求測試

    詳解Go語言中Get/Post請求測試

    這篇文章主要為大家詳細介紹了Go語言中的環(huán)境安裝以及Get和Post請求接口的測試,文中的示例代碼講解詳細,感興趣的可以跟隨小編一起學(xué)習(xí)一下
    2022-06-06
  • 如何使用騰訊云go sdk 查詢對象存儲中最新文件

    如何使用騰訊云go sdk 查詢對象存儲中最新文件

    這篇文章主要介紹了使用騰訊云go sdk 查詢對象存儲中最新文件,這包括如何創(chuàng)建COS客戶端,如何逐頁檢索對象列表,并如何對結(jié)果排序以找到最后更新的對象,我們還展示了如何優(yōu)化用戶體驗,通過實時進度更新和檢索多個文件來改進程序,需要的朋友可以參考下
    2024-03-03

最新評論