将protobuf字段的类型从double更改为float

Posted

tags:

篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了将protobuf字段的类型从double更改为float相关的知识,希望对你有一定的参考价值。

我在服务中使用原始消息将数据存储在各个位置

我的信息是这样的:

message Matrix 
  double width = 1;
  double height = 2;
  repeated double entries = 3;

[我的团队认为Matrix消息太大,将类型更改为float似乎是实现减少有效负载大小的一种简便方法。但是,当我在此处将原型定义更改为使用float而不是double并尝试读取旧数据(在Python阅读器中)时,它看起来已损坏。

我想到的一个选项是为每个字段添加一个新的float选项:

message Matrix 
  oneof r_oneof 
    double width_d = 1;
    float width_f = 4;
  
  oneof c_oneof 
    double height_d = 2;
    float height_f = 5;
  
  oneof e_oneof 
    repeated double entries_d = 3;
    repeated float entries_f = 6;
  

然后我的反序列化代码可以检查字段中的每个字段是double还是float字段。这可行,但感觉像是笨拙的设计模式。

在此示例中,还有另一种方法可提供与旧数据的向后兼容性吗?

答案

我认为您的想法正确。只要您以旧格式存储数据,您肯定会希望将旧字段用相同的数值作为键。协议缓冲区的一大优点是,未设置的字段实际上是免费的,因此您可以根据需要添加任意多个字段。

我要做的是跳过oneofs并重命名旧字段:

message Matrix 
  // Values in these fields should be transitioned to floats
  double deprecated_width = 1;
  double deprecated_height = 2;
  repeated double deprecated_entries = 3;

  float width = 4;
  float height = 5;
  repeated float entries = 6;

然后,每当您从持久性存储中读取Matrix时,都将不赞成使用的字段中的所有值移动到不赞成使用的字段中,并写回结果。这应该有助于向浮点数的增量迁移。

我将提到您可能已经知道的另一件事:协议缓冲区不在乎字段名称。序列化和反序列化由字段ID完成。这意味着我们可以自由地重命名字段,只要操作它们的代码同样得到更新即可。

在将来完成迁移的某个时候,终止迁移代码并删除不赞成使用的字段,但保留旧的ID:

message Matrix 
  reserved 1, 2, 3;
  float width = 4;
  float height = 5;
  repeated float entries = 6;

这可确保所有旧格式的杂散消息在反序列化时都会爆炸,而不会导致数据损坏。

希望这会有所帮助!

以上是关于将protobuf字段的类型从double更改为float的主要内容,如果未能解决你的问题,请参考以下文章

将 Django 模型字段的类型从 CharField 更改为 ForeignKey

将字段输入类型从隐藏更改为文本

尝试将 MYSQL 的表字段类型从 BLOB 更改为 JSON

协议缓冲区:将字段类型从字符串更改为字符串值向后兼容?

SQL Server 2012 如何将列的数据类型从位更改为日期字段?

scala - 高阶函数将类型T更改为Nothing