当前位置: 首页 > 面试题库 >

编码/解码JSON golang中的多类型字段

姜正初
2023-03-14
问题内容

我想创建一个结构,其中一个字段可以举行一些特殊类型的,比如说的数据intstringCustomType。我想将此结构从JSON解码/编码。我们如何在go
/ golang中实现这一目标?

例如,我具有以下定义的结构:

type MyData struct {
  Name  string                                    `json:"name"`
  Value int32                                     `json:"value"`
  Param <can be either int, string or CustomType> `json:"param"`
}

哪里CustomType

type CustomType struct {
  Custom bool `json:"custom"`
}

假设我需要将以下JSON解组到上述struct中MyData

{
  "name": "Hello",
  "value": 32
  "param": "World"
}

还有这个:

{
  "name": "Hello",
  "value": 32
  "param": 100
}

而且这个还:

{
  "name": "Hello",
  "value": 32
  "param": {
     "custom": true
  }
}

我该如何实现?

我可以自己定义MarshalJSONUnmarshalJSON继续MyData实现吗?

还是有一种定义自定义类型的方法,例如说IntOrStringOrCustom并定义MyData

type MyData struct {
  Name  string              `json:"name"`
  Value int32               `json:"value"`
  Param IntOrStringOrCustom `json:"param"`
}

然后定义MarshalJSONUnmarshalJSON继续IntOrStringOrCustom

我也看到过json.RawMessage。我们可以在这里以某种方式使用它吗?

使用的问题interface{}是,我将不得不在尝试使用此数据的任何地方编写编码/解码逻辑。还是有一种优雅的方式做到这一点interface{}


问题答案:

更新。interface会自动很好地编码和解码为JSON。如果您希望控制类型,则可以添加特殊字符UnmarshalJSON并在其中进行检查:

type TheParam interface{}

type MyData struct {
    Name  string   `json:"name"`
    Value int32    `json:"value"`
    Param TheParam `json:"param"`
}

type myData MyData

func (m *MyData) UnmarshalJSON(b []byte) error {
    var mm myData
    if err := json.Unmarshal(b, &mm); err != nil {
        return err
    }
    switch mm.Param.(type) {
    case float64, string, map[string]interface{}:
        *m = MyData(mm)
        return nil
    default:
        return InvalidFieldTypeError{value: mm.Param}
    }
    return nil
}

类型InvalidFieldTypeError可能方便返回此类错误,并且可以将其定义为:

type InvalidFieldTypeError struct {
    value interface{}
}

func (e InvalidFieldTypeError) Error() string {
    return fmt.Sprintf("Field type '%T' is not valid for MyData", e.value)
}

整个示例:https://play.golang.org/p/MuW6gwSAKi

我也想推荐这篇文章https://attilaolah.eu/2013/11/29/json-decoding-in-
go/



 类似资料:
  • 问题内容: 我有一个XML文档。一些字段具有自定义格式。例: 我想将其导入如下结构: 有什么方法可以实现自定义解码器,它将行字符串拆分成行数组()? 可以将Lines字段设置为字符串类型,并在xml导入后进行拆分,但这似乎不是一个很好的解决方案。我有什么方法可以定义用于行分割的自定义解码器,并将其与xml解码器组合? 问题答案: 您可以通过定义符合接口的新类型来实现。因此,与其创建一个,而不是使用

  • 6. 字符类型与字符编码 字符常量或字符型变量也可以当作整数参与运算,例如: printf("%c\n", 'a'+1); 执行结果是b。 我们知道,符号在计算机内部也用数字表示,每个字符在计算机内部用一个整数表示,称为字符编码(Character Encoding),目前最常用的是ASCII码(American Standard Code for Information Interchange,

  • 问题内容: ’=?KOI8-R?B?W1JFUS0wMDI1NDEtNDc5NzddIO / h7yAi89TSz8rGwdLGz9IiIDs =?= \ r \ n \ t =?KOI8-R?B?Ry43MjkgKDEwKQ ==?=’ 如何将其转换为可读的内容?谢谢 ! 问题答案: email.header.decode_header(‘=?KOI8-R?B?W1JFUS0wMDI1NDEtN

  • 对于Java/general中有关此概念的任何好的参考资料,我们将不胜感激。

  • 问题内容: 这是我尝试的错误消息。我究竟做错了什么? UnicodeEncodeError:’ascii’编解码器无法在位置37编码字符u’\ xa0’:序数不在范围内(128) UnicodeDecodeError:’ascii’编解码器无法解码位置37的字节0xc2:序数不在范围内(128) 问题答案: 您无法解码,也无法编码。尝试以另一种方式进行操作。