赞
踩
简单设计协议, 通过自带工具转换成为对应的语言代码, 协议是二进制协议, 设计时只需要描述各个类的关系, 简单明了
设计协议是在fileName.proto文件中, 其中fileName是自己定义, 在通过protoc转换成为对应的代码。
关键字:
基本语法
//指定版本 使用protobuf3
syntax = "proto3";
message Account {
//账号
uint64 ID = 1;
//名字
string name = 2;
//密码
string password = 3;
}
语法很简单, 上面例子就是指定使用protob3, 然后定义了一个Account类, 里面包含ID, name, password, 对应的类型是 uint64, string, string。
所以基本的语法规则跟C++类似。 只不过多了后面变量的编号。
生成代码:
需要生成什么语言的代码需要直接指定,例如C++
protoc --cpp_out=./ project.proto
protoc
是工具名, 可以直接运行的命令。
--cpp_out
是参数, 指定生成C++代码, =后面指定生成的目录。
project.proto
是定义的文件。
一共会生成两个文件。 project.pb.h
和 project.pb.cc
其中有生成的Account类中有这几个设置属性的方法
void clear_name(); static const int kNameFieldNumber = 2; const std::string& name() const; void set_name(const std::string& value); void set_name(std::string&& value); void set_name(const char* value); void set_name(const char* value, size_t size); std::string* mutable_name(); std::string* release_name(); void set_allocated_name(std::string* name); // string password = 3; void clear_password(); static const int kPasswordFieldNumber = 3; const std::string& password() const; void set_password(const std::string& value); void set_password(std::string&& value); void set_password(const char* value); void set_password(const char* value, size_t size); std::string* mutable_password(); std::string* release_password(); void set_allocated_password(std::string* password); // uint64 ID = 1; void clear_id(); static const int kIDFieldNumber = 1; ::PROTOBUF_NAMESPACE_ID::uint64 id() const; void set_id(::PROTOBUF_NAMESPACE_ID::uint64 value);
及get/set方法。
可以直接操作该类的属性。
使用该代码
在要使用的代码中包含此头文件project.pb.h
直接使用该对象即可。编译的时候需要把project.pb.cc
编译, 并在链接的时候链接动态链接库 libprotobuf.so
demo
#include <iostream> #include <string> #include "project.pb.h" int main() { Account account; account.set_id(1000); account.set_name("name"); account.set_password("password"); //序列化 std::string s = account.SerializeAsString(); if(s.size() == 0) { std::cout << "error in SerializeAsString" << std::endl; } Account nAccount; //反序列化 if(nAccount.ParseFromString(s)) { std::cout << nAccount.id() << std::endl; std::cout << nAccount.name() << std::endl; std::cout << nAccount.password() << std::endl; } else { std::cout << "error in ParseFromString" << std::endl; } return 0; }
编译
project.pb.cc
也需要编译, 如果是工程中, 可以单独编译, 由于只有一个文件所以就放到一块编译了g++ demo.cpp project.pb.cc -lprotobuf -o main
输出结果为:
1000
name
password
message的嵌套
message就像类一样, 所以它也是可以嵌套的。
可以直接在message内写, 也可以在外部写, 但是要注意的是, 一个message内的编号不能重复。
所以令写一个message会节省编号。
节省编号的所有是节省空间。 前15号(0~15)用一个字节, 后面以此类推, 两个三个字节, 所以前15编号比较珍贵。
demo
//指定版本 使用protobuf3 syntax = "proto3"; message Account { //账号 uint64 ID = 1; //名字 string name = 2; //密码 string password = 3; //宠物狗 Dog dog = 4; } message Dog { string name = 0; bool sex = 1; }
还有几个比较重要的方法
set_allocated_dog
dog不是必须的, 是类的名字。 可以是其他的名字
除了这些方法之外还有一些clear之类的方法, 需要可以看文档或者给的头文件。
oneof 是设置多个属性中的一个, 例如, 我的宠物可以是狗, 也可以是猫, 但是每个人只有一个的话。 设置两个占的空间就有点大。 因此只需要有一个就够了, 所以这个oneof就像union一样。
//指定版本 使用protobuf3 syntax = "proto3"; message Account { //账号 uint64 ID = 1; //名字 string name = 2; //密码 string password = 3; //宠物 oneof pet { Dog dog = 4; Cat cat = 5; } } message Dog { string name = 1; bool sex = 2; } message Cat { string name = 1; //属性可以与Dog不同 }
has_cat
或者 has_dog
方法用于检测是否有cat/dogCopyright © 2003-2013 www.wpsshop.cn 版权所有,并保留所有权利。