我正在使用协议缓冲区,一切正常.除了我不明白的事实 - 为什么我需要proto文件中的编号标签:
message SearchRequest {
required string query = 1;
optional int32 page_number = 2;
optional int32 result_per_page = 3;
}
Run Code Online (Sandbox Code Playgroud)
当然,我已经阅读了文档:
如您所见,消息定义中的每个字段都有一个唯一的编号标记.这些标记用于以消息二进制格式标识字段,并且在使用消息类型后不应更改.
我不明白如果我改变它会有什么不同.(我将创建一个新的原型并编译它 - 所以它为什么关心?)
原型定义中的编号字段消除了对版本检查的需要,这是对协议缓冲区的设计和实现的明确说明的动机之一.正如开发人员文档所述,协议的设计部分是为了避免像这样检查协议版本的"丑陋代码":
if (version == 3) {
...
} else if (version > 4) {
if (version == 5) {
...
}
...
}
Run Code Online (Sandbox Code Playgroud)
题
它只是我还是完全不清楚?
让我以不同的方式问它:
如果我有一个类似上述文件的proto文件,然后我将其更改为:
message SearchRequest {
required string query = 3; //reversed order
optional int32 page_number = 2;
optional int32 result_per_page = 1;
}
Run Code Online (Sandbox Code Playgroud)
它关心什么?我重新编译并添加文件(我在上周已多次完成).
我错过了什么?你能为这个编号标签提供人对人的解释吗?
Rot*_*tem 30
编号标签用于在序列化和反序列化数据时匹配字段.
显然,如果更改编号方案,并将此更改应用于序列化器和反序列化器,则没有问题.
考虑不过,如果你与第一编号方案保存的数据,并与第二个加载它,它会尝试加载query到result_per_page,和反序列化可能会失败.
现在,为什么这有用?假设您需要在数据中添加另一个字段,很久就会使用模式:
message SearchRequest {
required string query = 1;
optional int32 page_number = 2;
optional int32 result_per_page = 3;
optional int32 new_data = 4;
}
Run Code Online (Sandbox Code Playgroud)
因为您明确地给它一个数字,所以您的反序列化器仍然能够加载使用旧编号方案序列化的数据,而忽略了对不存在的数据进行反序列化.
| 归档时间: |
|
| 查看次数: |
6860 次 |
| 最近记录: |