protobuf篇:介紹、安裝、測試
愿打開此篇對你有所幫助。

@[toc]
關于 Protobuf3 的介紹,有前輩整理了,我就偷個懶:Protobuf3詳細介紹
PB、JSON、XML
綜上所述目前最好的設計消息數據包方式是服務器和客戶端通信協議推薦用protobuf,服務器存入數據庫時用json。
安裝
工欲善其事,必先利其器。
1、從github上下載自己所需版本:https://github.com/protocolbuffers/protobuf/releases/ 2、解壓 3、進入目錄 4、./configure 5、make && make install 6、vi /etc/profile,追加一下內容:
#(動態庫搜索路徑) 程序加載運行期間查找動態鏈接庫時指定除了系統默認路徑之外的其他路徑 export LD_LIBRARY_PATH=$LD_LIBRARY_PATH:/usr/local/protobuf/lib/ #(靜態庫搜索路徑) 程序編譯期間查找動態鏈接庫時指定查找共享庫的路徑 export LIBRARY_PATH=$LIBRARY_PATH:/usr/local/protobuf/lib/ #執行程序搜索路徑 export PATH=$PATH:/usr/local/protobuf/bin/ #c程序頭文件搜索路徑 export C_INCLUDE_PATH=$C_INCLUDE_PATH:/usr/local/protobuf/include/ #c++程序頭文件搜索路徑 export CPLUS_INCLUDE_PATH=$CPLUS_INCLUDE_PATH:/usr/local/protobuf/include/ #pkg-config 路徑 export PKG_CONFIG_PATH=/usr/local/protobuf/lib/pkgconfig/
7、vi /etc/ld.so.conf,追加/usr/local/protobuf/lib 8、/sbin/ldconfig -v 9、protoc --version
如何寫一個PB文件
也有proto3,都可以吧,我最開始接觸的是2,就翻譯 2 吧。
官網地址:https://developers.google.cn/protocol-buffers/docs/proto,有興趣的朋友可以自行查閱。
好吧,建議自己打開看,我不全翻譯,就看到一些覺得比較重要的我搬過來。
Protobuf消息定義
你首先需要在一個 .proto 文件中定義你需要做串行化的數據結構信息。每個ProtocolBuffer信息是一小段邏輯記錄,包含一系列的鍵值對。
消息由至少一個字段組合而成,類似于C語言中的結構。每個字段都有一定的格式。
字段格式:限定修飾符① | 數據類型② | 字段名稱③ | = | 字段編碼值④ | [字段默認值⑤]
這里有個非常簡單的 .proto 文件定義了個人信息:
message Person { required string name=1; required int32 id=2; optional string email=3; enum PhoneType { MOBILE=0; HOME=1; WORK=2; } message PhoneNumber { required string number=1; optional PhoneType type=2 [default=HOME]; } repeated PhoneNumber phone=4; }
Required: 表示是一個==必須字段==,必須相對于發送方,在發送消息之前必須設置該字段的值,對于接收方,必須能夠識別該字段的意思。發送之前沒有設置required字段或者無法識別required字段都會引發編解碼異常,==導致消息被丟棄==。
Optional:表示是一個==可選字段==,可選對于發送方,在發送消息時,可以有選擇性的設置或者不設置該字段的值。對于接收方,如果能夠識別可選字段就進行相應的處理,==如果無法識別,則忽略該字段==,消息中的其它字段正常處理。—因為optional字段的特性,很多接口在升級版本中都==把后來添加的字段都統一的設置為optional字段==,這樣老的版本無需升級程序也可以正常的與新的軟件進行通信,只不過新的字段無法識別而已,因為并不是每個節點都需要新的功能,==因此可以做到按需升級和平滑過渡==。
Repeated:表示該字段可以包含0~N個元素。其特性和optional一樣,但是每一次可以包含多個值。==可以看作是在傳遞一個數組的值==。
Protobuf定義了一套基本數據類型。幾乎都可以映射到C++\Java等語言的基礎數據類型.
N 表示打包的字節并不是固定。而是根據數據的大小或者長度。
關于message,類似于C語言中的結構包含另外一個結構作為數據成員一樣。
編碼值的取值范圍為 1~2^32(4294967296)。
不信往上面翻翻看,看看是不是都是數值。
==其中 1~15的編碼時間和空間效率都是最高的==,編碼值越大,其編碼的時間和空間效率就越低(相對于1-15),當然一般情況下相鄰的2個值編碼效率的是相同的,除非2個值恰好實在4字節,12字節,20字節等的臨界區。比如15和16.
==1900~2000編碼值為Google protobuf 系統內部保留值,建議不要在自己的項目中使用==。
protobuf 還建議把經常要傳遞的值把其字段編碼設置為1-15之間的值。
消息中的字段的編碼值無需連續,只要是合法的,并且==不能在同一個消息中有字段包含相同的編碼值==。
當在傳遞數據時,對于required數據類型,如果用戶沒有設置值,則使用默認值傳遞到對端。當接受數據是,對于optional字段,如果沒有接收到optional字段,則設置為默認值。
幾個注意事項
protobuf 接口文件可以像C語言的h文件一樣,分離為多個,在需要的時候通過 import導入需要的文件。
雖然可以在單個.proto文件中定義多種消息類型(例如消息,枚舉和服務),但當在單個文件中定義大量具有不同依賴性的消息時,也
可能導致依賴性膨脹。建議每個.proto文件包含盡可能少的消息類型。
避免名稱沖突,可以給每個文件指定一個package名稱,對于C++解析為名稱空間。
記得在開頭加上這兩句:
syntax = "proto3"; package demo;
枚舉的定義和C++相同,但是有一些限制。
枚舉值必須大于等于0的整數。
使用分號(;)分隔枚舉變量而不是C++語言中的逗號(,)
編譯PB
可編譯文件
首先,你要有一個PB文件可以拿去編譯,我知道你多半也沒有,沒事我這里有。
syntax = "proto3"; package demo; message Person { string name = 1; int32 id = 2; string email = 3; enum PhoneType { MOBILE = 0; HOME = 1; WORK = 2; } message PhoneNumber { string number = 1; PhoneType type = 2; } repeated PhoneNumber phone = 4; }
開始編譯
我下載了好多款,不過主語言是C++,畢竟打開一次不容易。打不開下載目錄的小伙伴可以私信我拿。
打開cmd, cd到該目錄,protoc.exe的命令行參數格式如下:
protoc --proto_path=IMPORT_PATH --cpp_out=DST_DIR --java_out=DST_DIR --python_out=DST_DIR path/to/file.proto
編譯之后就會出現新的文件了。
閱覽文件
打開之后太長了,自己去看。我這里提幾點。
(1)proto中的package在C++中是namespace; (2)proto中的message在C++中是class,類里面有各個成員的set/get;基類是google::protobuf::Message。 (3)代碼中可以看見C++11中的移動構造和移動賦值函數。
搞技術的人不搞那些彎彎繞的,放碼過來吧。
放碼過來
proto
syntax = "proto2"; package tutorial; message Person { optional string name = 1; optional int32 id = 2; optional string email = 3; enum PhoneType { MOBILE = 0; HOME = 1; WORK = 2; } message PhoneNumber { optional string number = 1; optional PhoneType type = 2 [default = HOME]; } repeated PhoneNumber phones = 4; } message AddressBook { repeated Person people = 1; }
讀.cpp
#include
寫.cpp
#include
版權聲明:本文內容由網絡用戶投稿,版權歸原作者所有,本站不擁有其著作權,亦不承擔相應法律責任。如果您發現本站中有涉嫌抄襲或描述失實的內容,請聯系我們jiasou666@gmail.com 處理,核實后本網站將在24小時內刪除侵權內容。
版權聲明:本文內容由網絡用戶投稿,版權歸原作者所有,本站不擁有其著作權,亦不承擔相應法律責任。如果您發現本站中有涉嫌抄襲或描述失實的內容,請聯系我們jiasou666@gmail.com 處理,核實后本網站將在24小時內刪除侵權內容。