为了账号安全,请及时绑定邮箱和手机立即绑定

mapstructure 如何使用鉴别器来解码具体类型

mapstructure 如何使用鉴别器来解码具体类型

Go
饮歌长啸 2023-06-01 15:05:08
文档 ( https://github.com/mitchellh/mapstructure ) 提到了 mapstructure 解码的好处{  "type": "person",  "name": "Mitchell"}我正在寻找一个显示解码过程的示例,例如解组 aPerson或Petclass
查看完整描述

1 回答

?
胡说叔叔

TA贡献1804条经验 获得超8个赞

该库仅将地图映射到结构。它不进行特定于类型的解码。引用其文档:

如果不首先从 JSON 中读取“类型”字段,我们可能无法填充特定结构。我们总是可以对 JSON 进行两次解码(首先读取“类型”,然后再读取其余部分)。然而,将它解码成一个结构要简单得多map[string]interface{},读取“type”键,然后使用类似这个库的东西将它解码成正确的结构。

它所提供的只是您只需将 JSON 源解析一次,然后将其解析为映射,然后您可以自己决定需要映射或解组为哪种类型。然后你就可以使用已经构建好的地图来填充你需要的类型。

看这个例子:

type Person struct {

    Name string `json:"name"`

}


type Credentials struct {

    User     string `json:"user"`

    Password string `json:"password"`

}


func main() {

    for _, src := range []string{srcPerson, srcCredentials} {

        var m map[string]interface{}

        if err := json.Unmarshal([]byte(src), &m); err != nil {

            panic(err)

        }


        switch m["type"] {

        case "person":

            var p Person

            if err := mapstructure.Decode(m, &p); err != nil {

                panic(err)

            }

            fmt.Printf("%T %+v\n", p, p)

        case "credentials":

            var c Credentials

            if err := mapstructure.Decode(m, &c); err != nil {

                panic(err)

            }

            fmt.Printf("%T %+v\n", c, c)

        }

    }

}


const srcPerson = `{

  "type": "person",

  "name": "Mitchell"

}`


const srcCredentials = `{

  "type": "credentials",

  "user": "bob",

  "password": "secret"

}`

输出:


main.Person {Name:Mitchell}

main.Credentials {User:bob Password:secret}


查看完整回答
反对 回复 2023-06-01
  • 1 回答
  • 0 关注
  • 129 浏览
慕课专栏
更多

添加回答

举报

0/150
提交
取消
意见反馈 帮助中心 APP下载
官方微信