You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

如何自定义JSON.Unmarshal将JSON解析为含城市切片的Go结构体

自定义JSON解析实现字段映射

要实现这个需求,确实可以通过自定义json.Unmarshaler接口的UnmarshalJSON方法来完成,具体代码实现如下:

package main

import (
	"encoding/json"
	"fmt"
)

type User struct {
	Username string
	Name     string
	Cities   []string
}

// 自定义UnmarshalJSON方法,实现json.Unmarshaler接口
func (u *User) UnmarshalJSON(data []byte) error {
	// 定义临时结构体,完全匹配JSON的结构
	type tempUser struct {
		Username  string `json:"username"`
		Name      string `json:"name"`
		Locations []struct {
			City string `json:"city"`
			// 忽略country字段,不需要定义对应字段
		} `json:"locations"`
	}

	var temp tempUser
	// 先把JSON数据解析到临时结构体
	if err := json.Unmarshal(data, &temp); err != nil {
		return err
	}

	// 将临时结构体的字段映射到目标User
	u.Username = temp.Username
	u.Name = temp.Name
	// 遍历Locations切片,提取所有City值到Cities
	u.Cities = make([]string, len(temp.Locations))
	for i, loc := range temp.Locations {
		u.Cities[i] = loc.City
	}

	return nil
}

func main() {
	// 测试用的JSON字符串
	jsonStr := `{ 
		"username":"bob", 
		"name":"Robert", 
		"locations": [ 
			{ "city": "Paris", "country": "France" }, 
			{ "city": "Los Angeles", "country": "US" } 
		] 
	}`

	var user User
	err := json.Unmarshal([]byte(jsonStr), &user)
	if err != nil {
		fmt.Println("解析失败:", err)
		return
	}

	fmt.Printf("解析结果: %+v\n", user)
}

逻辑说明

  1. 临时结构体tempUser的字段结构和输入JSON完全对应,这样标准库的json.Unmarshal可以正确解析出所有需要的字段,不需要的country字段直接不定义就会被自动忽略。
  2. 自定义的UnmarshalJSON方法中,先完成JSON到临时结构体的解析,再手动把临时结构体的字段值映射到目标User结构体,重点是遍历Locations切片提取所有City值到Cities字段。
  3. 代码包含错误处理,确保解析失败时能返回具体错误信息。

内容的提问来源于stack exchange,提问作者Jim Webb

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.07.21 15:17:19