Protocol Buffer详解

ProtoBuf详解 protobuf的介绍与使用 阅读详情

protobuf简介

Protocol Buffer是一种支持多平台、多语言、可扩展的的数据序列化机制,相较于XML来说,protobuf更小更快更简单,支持自定义的数据结构,用protobu编译器生成特定语言的源代码,如C++、Java、Python,目前protoBuf对主流的编程语言都提供了支持,非常方便的进行序列化和反序列化。

一、Message定义

这里简单的给出一个例子,是一个搜索请求的message格式

syntax = "proto3”;//指定proto版本,默认为proto2,而且改行必须是第一行

//message包含多个种类的fields
message SearchRequest {
  string query = 1;
  int32 page_number = 2;
  int32 result_per_page = 3;
}

上述例子中fields的种类都是数值型的(string和int32),当然也可以指定更加复杂的fields,比如枚举类型enum,或者是嵌套的message类型

1、分配field编号

上述例子中每个field都被分配了一个编号,这个编号是这个field的唯一标识,其中需要注意的是,标识1-15在编码的时候只占用一个字节,16-2047占用两个字节,所以为了进一步优化我们的程序,对于那种经常出现的element,建议使用1-15来作为他们的唯一标识,对那些不被经常使用的element,建议使用16-2047,编号的范围是1-2^29(19000-19999是系统预留的,不要使用)

2、field类型

message当中的field类型包含以下两种(proto3):

(1)singular

(2)repeated:该类型的field可以在message中重复使用(类似于数组),他们的顺序会被保存,通过索引进行检索,数值类型的repeated默认使用packed编码方式

3、多message结构

在一个proto文件中可以定义多个protobuf

4、reserved field类型

在开发过程中可能会涉及到对proto文件中message各个fields的修改,可能是更新、删除某个field及其表示,这样可能会导致调用的服务失败。其中一个防止这种问题的方式是,确保你要删除的field的标识(或是名字)是reserved,具体protobuf的编译器会决定未来这个field表示能否被使用

//数字标识和命名不能在同一条语句中混合声明

message Foo {
  reserved 2, 15, 9 to 11;
  reserved "foo", "bar";
}

二、数值类型

具体proto类型对应生成类中的类型可以参考官方文档

https://developers.google.com/protocol-buffers/docs/proto3#scalar
​developers.google.com/protocol-buffers/docs/proto3#scalar

三、默认值

对于string和byte类型,默认值为空;对于bool类型,默认值是false;对于数值类型,默认值是0;对于枚举类型,默认值是第一个枚举值,默认为0;对于message类型,默认值由编程语言决定;对于repeated field,默认值为空

四、枚举类型

当采用枚举类型的之后,枚举中的值都是预先定义好的,对于上述例子,我们可以再额外增加一个枚举类型corpus,具体如下

message SearchRequest {
  string query = 1;
  int32 page_number = 2;
  int32 result_per_page = 3;
  enum Corpus {
    UNIVERSAL = 0;
    WEB = 1;
    IMAGES = 2;
    LOCAL = 3;
    NEWS = 4;
    PRODUCTS = 5;
    VIDEO = 6;
  }
  Corpus corpus = 4;
}

通常枚举类型的第一个值初始化为0,而且在message中使用枚举类型,必须要给定一个为0的值,而且这个为0的值应该为第一个元素

也可以给不同的元素以相同的alias,但是需要指定option allow_alias = true;具体如下

enum EnumAllowingAlias {
  option allow_alias = true;
  UNKNOWN = 0;
  STARTED = 1;
  RUNNING = 1;
}
enum EnumNotAllowingAlias {
  UNKNOWN = 0;
  STARTED = 1;
  // RUNNING = 1;  // Uncommenting this line will cause a compile error inside Google and a warning message outside.
}

初次之外枚举类型不仅可以定义在message内部,也可以定义在message外部,而且在不同message中可以重用enum。

在更改枚举类型field时,为保证系统运行正常,同样可以指定reserved 数字标识和命名

五、使用其他message类型

1、同文件引用

具体如下:

message SearchResponse {
  repeated Result results = 1;
}
message Result {
  string url = 1;
  string title = 2;
  repeated string snippets = 3;
}

2、不同文件引用

引用其他proto文件中定义好的message类型,具体如下

import “myproject/other_protos.proto”;
有时我们会对引用的proto文件进行更改,比如将其内容移动到另外一个地方,这样我们就需要对调用方import路径进行更改,当调用方非常多的时候,这种方法是非常低效的,protobuf提供一种机制,我们可以在原有位置提供一个新位置proto文件的“副本”,通过使用import public表示来实现,具体可以参考如下例子

// new.proto
// All definitions are moved here

// old.proto
// This is the proto that all clients are importing.
import public "new.proto";
import "other.proto";

// client.proto
import "old.proto";
// You use definitions from old.proto and new.proto, but not other.proto

这时编译器就会在某些固定目录下查询import的proto文件(具体在命令行编译的时候,由-I/—proto_path指定),如果上述路径找不到,编译器会在调用路径进行查找。通常将—proto_path设置为项目的根目录,然后import的时候使用完整的路径名

3、使用proto2中的message类型

proto2中的枚举类型无法直接使用

六、嵌套类型

具体如下

message SearchResponse {
  message Result {
    string url = 1;
    string title = 2;
    repeated string snippets = 3;
  }
  repeated Result results = 1;
}

在parent message之外调用嵌套的message可以用如下方式:SearchResponse.Result,嵌套结构可以更加复杂,具体如下:


```java
message Outer {                  // Level 0
  message MiddleAA {  // Level 1
    message Inner {   // Level 2
      int64 ival = 1;
      bool  booly = 2;
    }
  }
  message MiddleBB {  // Level 1
    message Inner {   // Level 2
      int32 ival = 1;
      bool  booly = 2;
    }
  }
}

# 七、更新message类型
当现有的message已经无法满足现有业务需要,你需要更新你的message类型以支持更复杂的业务,这就涉及到向后兼容的问题了,为保证已有服务不受影响,需要遵守以下的一些规定

1、不要更改已经存在的fields的数字标识

2、如果添加新的field,利用旧代码序列化得到的message可以使用新的代码进行解析,你需要记住各个元素的默认值。新代码创建的field同样可以由旧代码进行加解析

3、field可以被删除,但是需要保证其对应的数字标识不再被使用,你可以通过加前缀的方式来重新使用这个field name,或者指定数字标识为reserved来避免这种情况

4、int32、int64、uint32、uint64、bool这些类型都是互相兼容的,并不会影响前向、后向兼容性

5、sint32和sint64之间是互相兼容的,但是和其他数字类型是不兼容的

6、string和bytes是互相兼容的,只要使用的是UTF-8编码

7、如果byte包含message的编码版本,则嵌套的message和bytes兼容

8、flexed32兼容sfixed32,fixed64,sfixed64

9、enum兼容 int32, uint32, int64, and uint64。对于这个值在转化时,不同语言的客户端处理方式会有所不同


Protobuf——Protocol Buffer详解(1) 最近在学习项目的时候需要用到protobuf进行序列与反序列化,由于是第一次接触protobuf,所以做个小总结。我们知道,当我们想要将内存中的对象状态保存到一个文件或者存到数据库的时候,或者在进行网络传输的时候,我们无法直接传输数据(因为接收方会无法分辨),所以我们就需要序列化与反序列化,将一个对象转换为字节序,再将字节序转换为一个完整的对象的过程。 阅读详情

相关推荐

详解Python Google Protocol Buffer

本篇主要介绍如何在Python语言中使用Google Protocol Buffer(后续都简写为PB), 包括以下几个部分: 为什么要使用PB? 安装Google PB 自定义.proto 文件 编译.proto文件 解析目标py文件 序列化和反序列化 更复杂的Message 动态编译 为什么要使用PB? PB(Protocol Buffer)是 Google 开发的用于结构化数据交换格式,作为腾讯云日志服务标准写入格式。因此用于写入日志数据前,需要将日志原始数据序列化为 PB 数据流后通过 API

职场亮哥 990

Protocol Buffer

一、Protocol Buffer 与 XML、JSON 的区别 Protocol Buffer 和 XML、JSON一样都是结构数据序列化的工具,但它们的数据格式有比较大的区别: 首先,Protocol Buffer 序列化之后得到的数据不是可读的字符串,而是二进制流 其次,XML 和 JSON 格式的数据信息都包含在了序列化之后的数据中,不需要任何其它信息就能还原序列化之后的数据;但使用 ...

Chain的博客 725

【保姆级】Protobuf详解及入门指南

Protobuf(Protocol Buffers)协议😉 Protobuf 是一种由 Google 开发的二进制序列化格式和相关的技术,它用于高效地序列化和反序列化结构化数据,通常用于网络通信、数据存储等场景。

aqin1012的博客 3万+

ProtocolBuffers(protobuf)详解

Protocol Buffers(通常简称为protobuf)是Google公司开发的一种数据描述语言,它能够将结构化数据序列化,可用于数据存储、通信协议等方面。这种序列化格式很灵活、高效、自动化,不依赖于语言和平台并且可扩展性极强。使用protobuf时,您只需将数据结构定义一次(使用.proto文件定义),便可以使用特别生成的源代码轻松地使用不同的数据流完成对这些结构数据的读写操作,即使使用不同的语言(protobuf的跨语言支持特性)。

技术人集结地 5190

SystemVerilog实战:AXI Stream协议从零搭建(附完整代码解析)

本文详细介绍了如何使用SystemVerilog从零搭建AXI Stream协议,包括核心信号解析、接口设计、主从设备实现及验证环境构建。通过完整的代码示例和工程实践技巧,帮助开发者掌握AXI Stream在FPGA/ASIC设计中的高效数据传输方法,特别适合视频处理和网络数据传输等应用场景。

weixin_29207439的博客 359

泛微OA自定义post接口和路径(无侵入)

泛微OA自定义post接口和路径(无侵入)

技术分享 3868

Protocol Buffer 技术详解

该系列Blog的内容主体主要源自于Protocol Buffer的官方文档,而代码示例则抽取于当前正在开发的一个公司内部项目的Demo。这样做的目的主要在于不仅可以保持Google文档的良好风格和系统性,同时再结合一些比较实用和通用的用例,这样就更加便于公司内部的培训,以及和广大网友的技术交流。需要说明的是,Blog的内容并非line by line的翻译,其中包含一些经验性总结,与此同时,对于一

mao8474的专栏 500

【unity小技巧】常用的方法属性和技巧汇总(长期更新,2025/07/02更新)

Unity开发技巧摘要 本文汇总了Unity开发中的实用技巧,包括移动控制、力应用、物体翻转、单例模式实现等。移动方面介绍了MoveTowards、MovePosition、Translate等方法的区别与应用场景;力应用部分详解了AddForce系列方法的参数和使用方式;物体翻转对比了三种实现方案;单例模式提供了标准实现和泛型优化版本;还收录了绝对值计算、鼠标检测、旋转控制、数值取整等实用代码片段。这些经过验证的技巧能有效提升开发效率,文章将持续更新补充新的实用内容。

向宇的博客,专注php/web全栈 unity游戏开发,欢迎大家评论纠错 3347

Protocol Buffer技术详解

一、生成目标语言代码。       下面的命令帮助我们将MyMessage.proto文件中定义的一组Protocol Buffer格式的消息编译成目标语言(Java)的代码。至于消息的内容,我们会在后面以分段的形式逐一列出,同时也会在附件中给出所有源代码。       protoc -I=./message --java_out=./src ./MyMessage.proto      

xiaozhu0301的博客 440

SAP UI5 本地开发工具 fiori-tools-proxy 中间件详解及使用场景

该中间件基于 http-proxy-middleware 库实现,分为 ui5 资源代理和 backend 代理两大模式,并可与 fiori run 或 ui5 serve 命令无缝集成,通过配置 ui5.path、ui5.url 以及 backend.path、backend.url 等参数,实现与目标系统的灵活对接和安全配置 (就后端系统代理而言,fiori-tools-proxy 内置 @sap-ux/backend-proxy-middleware,可将以指定前缀(如。

2007 年 ~ 2025 年,深耕 SAP 技术 18 年 516

数字电视中的AD(Audio Description)音频描述技术详解

AD(Audio Description)音频描述是一种辅助技术,旨在帮助视障人士更好地理解视觉内容。通过在节目或视频的自然停顿处插入额外的语音叙述来解释屏幕上的视觉信息,如人物动作、场景变化、文字说明等,从而让视力受损的人士也能获得完整的观影体验。AD服务不仅限于电视广播,也广泛应用于电影、剧院表演、在线视频平台等领域。PID:用于标识和区分不同的音频流。PMT表:提供每个音频流的详细信息,包括PID、编解码器类型和语言代码。时间戳:PTS和DTS用于同步音频与视频内容。解复用。

以实战经验介绍行业知识 739

Protocol Buffer的详解,使用及原理

登录 | 注册 IBM 技术主题 软件下载 社区 技术讲座 搜索 developerWorks 打印本页面 用电子邮件发送本页面 新浪微博 人人网 腾讯微博 搜狐微博 网易微博 Digg Facebook Twitter Delicious Linked In

蒲公英的晴空 2835

100天精通Python(基础篇)——第22天:eval 函数基础以及危险警告

1. eval()函数的概念 2. eval()函数语法 3. 命名空间 4. 使用实例 1. 基本的数学运算 2. 字符串重复 3. 将字符串转换成列表 4. 将字符串转换成字典 5. 将字符串转成元祖 6. 与其它函数结合使用 7. globals参数案例 8. locals参数案例 5. eval函数的危险之处(重中之中)

努力让自己发光,对的人才能迎着光而来 15万+

protocol buffer 详解

Google protocol buffer 已经可以生成头文件和源文件了, 还是有问题的请看我的上一篇文章,里面有详解; 一、 生成测试用message: 这里先定义一个最简单的message,其中只是包含原始类型的字段。       option optimize_for = LITE_RUNTIME;       message LogonReqMessage {        

she5125658的专栏 823

NX二次开发 内部函数鼠标动态位置获取

内部函数鼠标动态位置获取

qq285503851的博客 3336

深度揭秘!用 DeepSeek 打造超智能电商客服系统全流程

摘要:本文围绕使用 DeepSeek 开发电商智能客服展开详细教程。先介绍前期准备,包括了解 DeepSeek、获取 API 权限与搭建开发环境。接着阐述数据收集预处理,结合电商业务逻辑实现商品与订单信息查询。还提及优化性能的方法,如模型微调、多轮对话管理和错误处理。然后说明了基于 Web 和云平台的部署方案。最后强调持续监控和改进的重要性,通过设置监控指标、收集分析用户反馈来优化系统,助力开发者打造高效电商智能客服。

专注于人工智能、软件开发、工控自动化、工厂数字化及智能化等领域,希望和大家共同进步! 7812

Protocol Buffer技术详解(语言规范)

该系列Blog的内容主体主要源自于Protocol Buffer的官方文档,而代码示例则抽取于当前正在开发的一个公司内部项目的Demo。这样做的目的主要在于不仅可以保持Google文档的良好风格和系统性,同时再结合一些比较实用和通用的用例,这样就更加便于公司内部的培训,以及和广大网友的技术交流。需要说明的是,Blog的内容并非line by line的翻译,其中包含一些经验性总结,与此同时,对于一

把握自己。 1459

Camera2Demo

在Camera2 的基础上进行封装,使得Camera2一堆初始化逻辑与Activity分离,降低耦合度,完成预览拍照并保存的操作

windows10 Protocol buffer配置详解

protocol buffer作为tensorflow的主要依赖包之一,是谷歌开发的一款处理结构化数据的工具,将结构数据转为数据流数据,意思大概就是这么个意思类似XML和JSON那样的结构化处理工具,但是相互之间还是存在较大的区别。protocol buffer序列化数据的解析速度是XML快20到100倍之间。 下载两个包: https://github.com/protocolbuffers/p...

qq_21294373的博客 1325

温度PID控制PLC程序

温度PID稳定控制程序,适用于欧姆龙PLC,对其他PLC也具有很大参考价值

迈瑞BS系列全自动生化分析仪LIS协议接口手册(内含HL7和ASTM)

迈瑞BS系列全自动生化分析仪LIS协议接口手册,内含HL7和ASTM)

上一篇: 算法笔记-lc-1114. 按序打印(多线程简单题)
下一篇: 分布式选举算法总结
Hell_potato777
博客等级 码龄6年 47粉丝 106原创
评论
成就一亿技术人!
拼手气红包6.0元
还能输入1000个字符
 
 条评论被折叠 查看
添加红包

请填写红包祝福语或标题

个

红包个数最小为10个

元

红包金额最低5元

当前余额3.43元 前往充值 >
需支付:10.00元
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付元
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值