《protobuf》基础语法

文章目录

  • 消息体定义
  • 字段规则
  • 编译选项
  • 实战:编写一个通讯录文件

消息体定义

  • 文件内定义
message Phone
{string number = 1;
}message PeopleInfo
{string name = 1;int32 age = 2;Phone phone = 3;
}
  • 内嵌定义
message PeopleInfo
{string name = 1;int32 age = 2;message Phone{string number = 1;}Phone phone = 3;
}
  • 文件外定义
// 文件 Phone.proto
syntax = "proto3";
package phone;message Phone
{string number = 1;
}
import "Phone.proto";
message PeopleInfo
{string name = 1;int32 age = 2;// 引⼊的⽂件声明了package,使⽤消息时,需要⽤ ‘命名空间.消息类型’ 格式phone.Phone phone = 3;
}

字段规则

消息的字段可以用下面几种规则来修饰:

  • singular :消息中可以包含该字段零次或⼀次(不超过⼀次)。proto3 语法中,字段默认使⽤该
    规则
  • repeated :消息中可以包含该字段任意多次(包括零次),其中重复值的顺序会被保留。可以理解为定义了⼀个数组。

续回上篇,继续完善contacts.proto文件的内容

syntax = "proto3";
package contacts;message PeopleInfo
{string name = 1;int32 age = 2;// 采用内嵌式message Phone{string number = 1;}// repeated 修饰词 修饰的变量相当于数组repeated Phone phone = 3;
}// 通讯录
message Contacts
{repeated PeopleInfo contacts = 1;
}

编译选项

补充上篇:

  • -h : protoc -h 表示帮助
    在这里插入图片描述
    上图是所有内容,下面重点讲解一下 - decode
  • decode
    在这里插入图片描述大概意思是:从标准输入读取给定类型的二进制消息,并以文本格式将其写入标准输出。消息类型必须在PROTO FILES或其导入中定义。

先看用法

protoc -decode=contacts.Contacts contacts.proto < contacts.bin

在这里插入图片描述
执行指令后,结果如下
在这里插入图片描述
这个编译条件可以快速查看序列化后二进制文件的内容,是一个很便捷的操作

查看二进制内容的工具还有hexdump

hexdump:是Linux下的一个二进制文件查看工具,它可以将二进制文件转换为ASCII、八进制、十进制、十六进制格式进行查看。
-C: 表示每个字节显示为16进制和相应的ASCII字符

hexdump -C 二进制文件名
eg:hexdump -C contact.bin

在这里插入图片描述

实战:编写一个通讯录文件

上面完善编写了contacts.proto文件,现在完成写文件write.cpp和读文件read.cpp,write.cpp文件主要用于将通讯录信息通过protobuf的序列化,然后写入contact.bin文件内,read.cpp文件主要用于通过protobuf的反序列化,对contact.bin文件内容的读取。

write.cpp的编写

#include<iostream>
#include<fstream>
#include"contacts.pb.h"
using namespace std;void AddPeopleInfo(contact2::PeopleInfo *people)
{cout << "--------------新增联系⼈--------------" << endl;cout << "请输⼊联系⼈姓名: ";string name;getline(cin, name);people->set_name(name);cout << "请输⼊联系⼈年龄: ";int age;cin >> age;cin.ignore(256, '\n');  // 清除缓冲区的内容,大于256或遇到'\n'停止people->set_age(age);for(int i = 1; ;++i){cout <<  "请输⼊联系⼈电话" << i << "(只输⼊回⻋完成电话新增): ";string number;getline(cin, number);if(number.empty()) break;people->add_phone()->set_number(number);}cout << "-------------添加联系⼈成功-------------" << endl;
}int main()
{contacts::Contacts con;fstream in("contact.bin", ios::in | ios::binary);if(!in)cout << "contact.bin not exist, it is being created now" << endl;// ParseFromIstream方法的作用: 读取in里的内容并将其反序列化保存起来else if(!con.ParseFromIstream(&in)){cerr << "Fail to parse" << endl;in.close();return -1;}in.close();// 写入通讯录信息// 前文有提到,repeated修饰的变量相当于数组,所以// con.add_contacts()就相当新分配了一个contacts变量AddPeopleInfo(con.add_contacts());fstream out("contact.bin", ios::out | ios::trunc | ios::binary);// SerializeToOstream方法的作用: 读取out里的内容并将其序列化保存起来if(!con.SerializeToStream(&out)){cerr << "Fail to serialize" << endl;out.close();return -1;}cout << "write success" << endl;out.close();return 0;
}

执行效果如下:
在这里插入图片描述
在这里插入图片描述

read.cpp的编写

#include <iostream>
#include <fstream>
#include "contacts.pb.h"using namespace std;void PrintfContacts(contact2::Contacts &con)
{cout << "------------- 通讯录  -------------" << endl;for(int i = 0; i < con.contacts_size(); ++i){cout << "========= 联系人 " << i+1 << " =========" << endl;const contact2::PeopleInfo people = con.contacts(i);cout << "姓名:" << people.name() << endl;cout << "年龄:" << people.age() << endl;for(int j = 0; j < people.phone_size(); ++j){auto phone = people.phone(j);cout << "号码" << j+1 << ":" << phone.number() << endl;}}cout << "-------------------------------" << endl;
}int main()
{contact2::Contacts con;fstream in("contact.bin", ios::in | ios::binary);if(!in)cout << "contact.bin not exist, it is being created now" << endl;else if(!con.ParseFromIstream(&in)){in.close();return -1;}PrintfContacts(con);in.close();return 0;
}

执行效果如下:
在这里插入图片描述

补充:主要函数的使用

  • bool ParseFromIstream(std::istream* input);
    Parse 系列的函数有很多,因为前面用了文件流提取内容,所以这里使用 Parse 系列的Istream()。
    作用:读取 input 里的内容并将其反序列化保存起来

  • add_contacts()
    因为 Contacts 里的 contacts 字段被 repeat 修饰,所以相当于数组,这个函数是专门新增一个 contacts 变量的。(ps:因为有contacts所以才是 add_contacts() ,如果是 其他 那么就会对应生成 add_其他()

  • bool SerializeToOstream(std::ostream* output) const;
    作用: 读取 output 里的内容并将其序列化保存起来

  • contacts_size();
    求变量个数(可以认为数组大小),注意 size 前面的名称是变量名称

  • set_变量名();
    代码里有出现,set_age(age),set_name(name),set_number(number) 没错,这些都是设置值的函数

以上函数均包含在 文件.pb.h 里,必要是时可以跳转进去里面学习函数使用,上面仅讲解了使用到的函数

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mzph.cn/news/73277.shtml

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

Vue3_pinia使用

安装 cnpm install pinia 新建store目录&#xff0c;在store目录下创建loginUser.js import { defineStore } from pinia import {ref} from vue export const userLoginStore defineStore(loginUser, () > {let loginUserInfo ref({})function setUserInfo(data){this.…

Vue中如何实现城市3D分布图

cityfenbu.vue <template><div ><el-card class"seriesmap-box-card"><div slot"header" class"clearfix"><span>城市分布图 (点击可下钻到县)</span></div><div><div class"series-ma…

【科研论文配图绘制】task8 总结与回顾

task8 总结与回顾&#xff0c;这次组队学习大致掌握了常见python绘图工具包的使用&#xff0c;整体上和matlab的语法类似&#xff0c;也是用画布形式控制元素的绘制。印象深刻的是seaborn的使用&#xff0c;在之前做波士顿房价预测时候先接触了seaborn绘制的散点图、直方图和核…

【C++从0到王者】第二十八站:二叉搜索树的应用

文章目录 前言一、Key模型二、Key/Value模型总结 前言 二叉搜索树的在现实世界的应用很广泛&#xff0c;比如Key模型&#xff0c;Key-Value模型就是常见的两种的模型 一、Key模型 K模型&#xff1a;K模型即只有key作为关键码&#xff0c;结构中只需要存储Key即可&#xff0c…

适用于Linux的Windows子系统(系统安装步骤)

目录 前言 一、WSL2安装 1.Microsoft参考文档&#xff08;推荐选择旧版 WSL 的手动安装步骤&#xff09; 2.开启子系统 二、Ubuntu安装 1.在Microsoft Store中获取ubuntu 2.运行ubuntu配置管理信息 3.ubuntu换源 三、WSL 与 Ubuntu的一些基础使用命令 四、Windows Terminal终端…

C++新特性:智能指针

一 、为什么需要智能指针 智能指针主要解决以下问题&#xff1a; 1&#xff09;内存泄漏&#xff1a;内存手动释放&#xff0c;使用智能指针可以自动释放 2&#xff09;共享所有权指针的传播和释放&#xff0c;比如多线程使用同一个对象时析构问题&#xff0c;例如同样的数据…

C#,《小白学程序》第十八课:随机数(Random)第五,方差及标准方差(标准差)的计算方法与代码

1 文本格式 /// <summary> /// 《小白学程序》第十八课&#xff1a;随机数&#xff08;Random&#xff09;第五&#xff0c;方差及标准方差&#xff08;标准差&#xff09;的计算方法与代码 /// 方差 SUM(&#xff08;Xi - X)^2 ) / n i0...n-1 X Average of X[i] ///…

《DevOps实践指南》- 读书笔记(二)

DevOps实践指南 Part 2 从何处开始5. 选择合适的价值流作为切入点5.1 绿地项目与棕地项目5.2 兼顾记录型系统和交互型系统5.3 从最乐于创新的团队开始5.4 扩大 DevOps 的范围5.5 小结 6. 理解、可视化和运用价值流6.1 确定创造客户价值所需的团队6.2 针对团队工作绘制价值流图6…

【广州华锐互动】电厂三维数字孪生大屏的功能和优势

在工业互联网的背景下&#xff0c;电厂三维数字孪生大屏系统正在逐渐成为电力行业的重要技术。通过创建电厂的虚拟模型&#xff0c;这个数字孪生系统可以实现对实际电厂的实时监控&#xff0c;预测维护需求&#xff0c;优化运营效率&#xff0c;甚至在某些情况下&#xff0c;能…

jmeter 线程组 Open Model Thread Group 阶梯式压测、高峰流量压测

简介 Open Model Thread Group 是5.4.1 版本中引入的一个实验性线程组&#xff0c;可以弹性模拟负载测试。例如设置多个线程模式&#xff0c;再根据这些线程模式调整不同的并发数、暂停时间。由于Open Model Thread Group 是一个实验性线程组&#xff0c;可能会存在一些限制和不…

2.9 PE结构:重建导入表结构

脱壳修复是指在进行加壳保护后的二进制程序脱壳操作后&#xff0c;由于加壳操作的不同&#xff0c;有些程序的导入表可能会受到影响&#xff0c;导致脱壳后程序无法正常运行。因此&#xff0c;需要进行修复操作&#xff0c;将脱壳前的导入表覆盖到脱壳后的程序中&#xff0c;以…

【群智能算法改进】一种改进的鹈鹕优化算法 IPOA算法[2]【Matlab代码#58】

文章目录 【获取资源请见文章第5节&#xff1a;资源获取】1. 原始POA算法2. 改进后的IPOA算法2.1 随机对立学习种群初始化2.2 动态权重系数2.3 透镜成像折射方向学习 3. 部分代码展示4. 仿真结果展示5. 资源获取 【获取资源请见文章第5节&#xff1a;资源获取】 1. 原始POA算法…

【JavaScript】在指定dom元素前面创建标签元素

一、基础操作过程 要在指定的DOM元素前面创建标签元素&#xff0c;有以下步骤&#xff1a; 获取指定的DOM元素&#xff1a;使用document.querySelector()或document.getElementById()等方法来获取指定的DOM元素。 const targetElement document.querySelector(#targetElement…

数字展厅有什么优势,一文了解数字展厅建设方案

引言&#xff1a; 在当今数字化风潮的席卷下&#xff0c;企业们正积极寻求创新的方式来吸引和互动他们的客户。数字展厅作为一种新型的虚拟宣传工具&#xff0c;已经开始引起广泛的关注。 一&#xff0e;什么是数字展厅&#xff1f; 数字展厅是一种基于虚拟现实&#xff08;V…

【前端】在Vue页面中引入其它vue页面 数据传输 相互调用方法等

主页面 home 从页面 headView 需求 在 home.vue 中引用 headView.Vue 方案: home.vue 代码: 只需要在home.vue 想要的地方添加 <headView></headView> <script>//聊天页面 import headView /view/headView.vueexport default {components: {headView},…

淘宝商品销量接口API更新(总销+精准月销API)

不少客户有获取淘宝商品销量的需求&#xff0c;淘宝商品销量接口主要用于以下业务场景。有不齐全的欢迎大家补充。 库存管理&#xff1a;商家可以通过接口获取到实时的销量信息&#xff0c;更好地进行库存管理。供应链计划&#xff1a;商家可以通过接口了解到商品的销售趋势&a…

Unity的UI面板基类

使用这个组件实现淡入淡出 public abstract class BasePanel : MonoBehaviour {//控制面板透明度 用于淡入淡出private CanvasGroup canvasGroup;//淡入淡出速度private float alphaSpeed 10;//隐藏还是显示public bool isShow false;//隐藏完毕后做的事private UnityAction …

企业电子招标采购系统源码Spring Boot + Mybatis + Redis + Layui + 前后端分离 构建企业电子招采平台之立项流程图

功能模块&#xff1a; 待办消息&#xff0c;招标公告&#xff0c;中标公告&#xff0c;信息发布 描述&#xff1a; 全过程数字化采购管理&#xff0c;打造从供应商管理到采购招投标、采购合同、采购执行的全过程数字化管理。通供应商门户具备内外协同的能力&#xff0c;为外部供…

Web安全——穷举爆破下篇(仅供学习)

Web安全 一、常见的端口服务穷举1、hydra 密码穷举工具的使用2、使用 hydra 穷举 ssh 服务3、使用 hydra 穷举 ftp 服务4、使用 hydra 穷举 mysql 服务5、使用 hydra 穷举 smb 服务6、使用 hydra 穷举 http 服务7、使用 hydra 穷举 pop3 服务8、使用 hydra 穷举 rdp 服务9、使用…

适用于基于晶圆键合的3D集成应用的高效单晶圆清洗

引言 不同的微电子工艺需要非常干净的表面以防止颗粒污染。其中&#xff0c;晶圆直接键合对颗粒清洁度的要求非常严格。直接晶圆键合包括通过简单地将两种材料的光滑且干净的表面接触来将两种材料连接在一起&#xff08;图1&#xff09;。在室温和压力下&#xff0c;两种材料表…