我正在为我的项目使用GOB编码,并且我发现(经过长时间的争斗)空字符串未被正确编码/解码。在我的代码中,我使用errormessage(字符串)来报告任何问题,这个错误消息大部分时间都是空的。如果我编码一个空字符串,它什么都没有,这给我一个解码的问题。我不想改变编码/解码,因为这些部分使用最多。 我如何告诉Go如何编码/解码空字符串?
实施例: Playground工作代码。 Playground无效代码。
答案 0 :(得分:1)
问题不是encoding/gob
模块,而是您为MarshalBinary
声明的自定义UnmarshalBinary
/ Msg
方法,这些方法无法正确往返一个空字符串。你可以通过两种方式来到这里:
摆脱MarshalBinary
/ UnmarshalBinary
方法并依赖GOB的结构默认编码。仅此变化不够,因为不会导出结构的字段。如果您愿意导出字段,那么这是最简单的选项:https://play.golang.org/p/rwzxTtaIh2
使用可以正确舍入空字符串的编码。一个简单的选择是使用GOB本身来编码struct字段:
func (m Msg) MarshalBinary() ([]byte, error) {
var b bytes.Buffer
enc := gob.NewEncoder(&b)
if err := enc.Encode(m.x); err != nil {
return nil, err
}
if err := enc.Encode(m.y); err != nil {
return nil, err
}
if err := enc.Encode(m.z); err != nil {
return nil, err
}
return b.Bytes(), nil
}
// UnmarshalBinary modifies the receiver so it must take a pointer receiver.
func (m *Msg) UnmarshalBinary(data []byte) error {
dec := gob.NewDecoder(bytes.NewBuffer(data))
if err := dec.Decode(&m.x); err != nil {
return err
}
if err := dec.Decode(&m.y); err != nil {
return err
}
return dec.Decode(&m.z)
}
您可以在此处试验此示例:https://play.golang.org/p/oNXgt88FtK
第一个选项显然更容易,但如果您的真实示例稍微复杂一点,则第二个选项可能会有用。但要注意自定义编码器:GOB包含一些旨在检测不兼容性的功能(例如,如果向结构中添加字段并尝试解码旧数据),这些功能在此自定义编码中缺失。