在項目中使用Protobuf協(xié)議實現(xiàn)數(shù)據(jù)傳輸(二)

上篇已經(jīng)簡單的分析了什么是ProtoBuf協(xié)議的優(yōu)缺點、簡單的環(huán)境配置、項目中的簡單使用和一些編寫.Proto文件的注意點桃熄,下面我們更加深入一下ProtoBuf的語法及高級使用(非常感謝Carson_Ho大神的博文指導(dǎo))

從Google官方例子進(jìn)行語法深入

Google官方例子:

syntax = "proto2";//聲明proto版本着茸,2.0與3.0以后語法差異很大

package tutorial;//// 關(guān)注1:包名

option java_package = "com.example.tutorial";
option java_outer_classname = "AddressBookProtos";//// 關(guān)注2:option選項

message Person {//// 關(guān)注3:消息模型
  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 phones = 4;
}

message AddressBook {
  repeated Person people = 1;
}

針對上述官方例子的注釋,下面一一分析

關(guān)注點1:包名

作用:防止不同 .proto 項目間命名 發(fā)生沖突

ProtoBuf包的解析過程如下

  • Protocol buffer 的類型名稱解析與 C++ 一致:從 最內(nèi)部 開始查找樟澜,依次 向外 進(jìn)行
    每個包會被看作是其父類包的內(nèi)部類
  • Protocol buffer 編譯器會解析 .proto文件中定義的所有類型名
    生成器會根據(jù) 不同語言 生成 對應(yīng)語言 的代碼文件
  • 即對 不同語言 使用了 不同的規(guī)則 進(jìn)行處理
  • Protoco Buffer提供 C++误窖、Java、Python 三種語言的 API

關(guān)注點2:option選項

作用:影響 特定環(huán)境下 的處理方式秩贰,但不改變整個文件聲明的含義

常用Option選項:(因為使用有限霹俺,簡單列舉常見的)

option java_package = "com.crf.jason.myapplication";
// 定義:Java包名
// 作用:指定生成的類應(yīng)該放在什么Java包名下
// 注:如不顯式指定,默認(rèn)包名為:按照應(yīng)用名稱倒序方式進(jìn)行排序
option java_outer_classname="Demo";
// 定義:類名
// 作用:生成對應(yīng).java 文件的類名(不能跟下面message的類名相同)
// 注:如不顯式指定萍膛,則默認(rèn)為把.proto文件名轉(zhuǎn)換為首字母大寫來生成
// 如.proto文件名="book.proto"吭服,默認(rèn)情況下,將使用 "BookOuterClass" 做為類名

option optimize_for = ***;
// 作用:影響 C++  & java 代碼的生成
// ***參數(shù)如下:
// 1. SPEED (默認(rèn))::protocol buffer編譯器將通過在消息類型上執(zhí)行序列化蝗罗、語法分析及其他通用的操作艇棕。(最優(yōu)方式)
// 2. CODE_SIZE::編譯器將會產(chǎn)生最少量的類,通過共享或基于反射的代碼來實現(xiàn)序列化串塑、語法分析及各種其它操作沼琉。
  // 特點:采用該方式產(chǎn)生的代碼將比SPEED要少很多, 但是效率較低桩匪;
  // 使用場景:常用在 包含大量.proto文件 但 不追求效率 的應(yīng)用中打瘪。
//3.  LITE_RUNTIME::編譯器依賴于運(yùn)行時 核心類庫 來生成代碼(即采用libprotobuf-lite 替代libprotobuf)。
  // 特點:這種核心類庫要比全類庫小得多(忽略了 一些描述符及反射 );編譯器采用該模式產(chǎn)生的方法實現(xiàn)與SPEED模式不相上下闺骚,產(chǎn)生的類通過實現(xiàn) MessageLite接口彩扔,但它僅僅是Messager接口的一個子集。
  // 應(yīng)用場景:移動手機(jī)平臺應(yīng)用
  • Google官方還提供了在ProtoBuf中允許 自定義選項并且使用,具體請參考:傳送門

關(guān)注點3:消息模型

作用:真正用于描述 數(shù)據(jù)結(jié)構(gòu)

在.proto消息模型中主要有 消息對象&字段

Protobuf中的消息對象

  • 一個消息對象(Message) = 一個 結(jié)構(gòu)化數(shù)據(jù)
  • 消息對象用 修飾符 message 修飾
  • 消息對象 含有 字段:消息對象(Message)里的 字段 = 結(jié)構(gòu)化數(shù)據(jù) 里的成員變量

注意:

  • 在一個.proto文件可以定義多個消息對象

      message Person{//level 0
          string name=1;
          int32 age=2;
           string email=3;
      ...
      }
      message Car{
       string carName=1;
      int32 price=2;
      }
    
  • 在一個消息對象里面可以定義另外一個消息對象(嵌套)

      message Person{//level 0
          string name=1;
          int32 age=2;
           string email=3;
      enum Phonetype{
           MOBILE=0;
          HOME=1;
      }
      message PhoneNumber{//level 1
       string number=1;
      }
      }
    

Protobuf中消息對象的字段

字段

組成:字段 = 字段修飾符 + 字段類型 +字段名 +標(biāo)識號(主要針對proto2以前版本)

// required int32 id = 1;

字段 = 字段類型 +字段名 +標(biāo)識號(主要針對proto3及以后版本)

int32 id = 1;
字段類型

一個消息對象 可以將 其他消息對象類型 用作字段類型

  • 使用同一個 .proto 文件里的消息類型

  • 使用 內(nèi)部消息類型

     先在 消息類型 中定義 其他消息類型 僻爽,然后再使用(嵌套)
    
         message Person{//level 0
             string name=1;
             int32 age=2;
             string email=3;
            enum Phonetype{
                MOBILE=0;
                HOME=1;
            }
             message PhoneNumber{//level 1
              string number=1;
              Person person=2;
             }
             PhoneNumber phoneNumber=4;//這里就是直接使用剛才定義的PhoneNumber消息類型
         }
         message Car{
             string carName=1;
             int32 price=2;
             Person.PhoneNumber phoneNumber=3;
         }
    
  • 使用 外部消息類型

     即外部重用虫碉,需要 用作字段類型的消息類型 定義在 該消息類型外部
    
         message Person{//level 0
             string name=1;
             int32 age=2;
             string email=3;
            enum Phonetype{
                MOBILE=0;
                HOME=1;
            }
             message PhoneNumber{//level 1
              string number=1;
              Person person=2;//這里就是使用外部消息類型 person
             }
             PhoneNumber phoneNumber=4;
         }
         message Car{
             string carName=1;
             int32 price=2;
             Person.PhoneNumber phoneNumber=3;
         }
    
  • 使用 外部消息的內(nèi)部消息類型

         message Person{//level 0
             string name=1;
             int32 age=2;
             string email=3;
            enum Phonetype{
                MOBILE=0;
                HOME=1;
            }
             message PhoneNumber{//level 1
              string number=1;
              Person person=2;
             }
             PhoneNumber phoneNumber=4;
         }
         message Car{
             string carName=1;
             int32 price=2;
             Person.PhoneNumber phoneNumber=3;//這里使用外部消息類型Person的PhoneNumber內(nèi)部消息類型
         }
    
  • 使用不同 .proto 文件里的消息類型

    作用:需要在 A.proto文件 使用 B.proto文件里的消息類型

    在 A.proto文件 通過導(dǎo)入( import) B.proto文件中來使用 B.proto文件 里的消息類型

  • 將 消息對象類型 用在 RPC(遠(yuǎn)程方法調(diào)用)系統(tǒng)

    具體實現(xiàn)請移步:大神博客

關(guān)于ProtoBuf在項目中的實踐的高級用法請關(guān)注:下一篇博客:在項目中使用Protobuf協(xié)議實現(xiàn)數(shù)據(jù)傳輸(三)

?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請聯(lián)系作者
  • 序言:七十年代末,一起剝皮案震驚了整個濱河市胸梆,隨后出現(xiàn)的幾起案子敦捧,更是在濱河造成了極大的恐慌,老刑警劉巖碰镜,帶你破解...
    沈念sama閱讀 206,013評論 6 481
  • 序言:濱河連續(xù)發(fā)生了三起死亡事件兢卵,死亡現(xiàn)場離奇詭異,居然都是意外死亡绪颖,警方通過查閱死者的電腦和手機(jī)秽荤,發(fā)現(xiàn)死者居然都...
    沈念sama閱讀 88,205評論 2 382
  • 文/潘曉璐 我一進(jìn)店門,熙熙樓的掌柜王于貴愁眉苦臉地迎上來柠横,“玉大人王滤,你說我怎么就攤上這事∽茵” “怎么了雁乡?”我有些...
    開封第一講書人閱讀 152,370評論 0 342
  • 文/不壞的土叔 我叫張陵,是天一觀的道長糜俗。 經(jīng)常有香客問我踱稍,道長,這世上最難降的妖魔是什么悠抹? 我笑而不...
    開封第一講書人閱讀 55,168評論 1 278
  • 正文 為了忘掉前任珠月,我火速辦了婚禮,結(jié)果婚禮上楔敌,老公的妹妹穿的比我還像新娘啤挎。我一直安慰自己,他們只是感情好卵凑,可當(dāng)我...
    茶點故事閱讀 64,153評論 5 371
  • 文/花漫 我一把揭開白布庆聘。 她就那樣靜靜地躺著,像睡著了一般勺卢。 火紅的嫁衣襯著肌膚如雪伙判。 梳的紋絲不亂的頭發(fā)上,一...
    開封第一講書人閱讀 48,954評論 1 283
  • 那天黑忱,我揣著相機(jī)與錄音宴抚,去河邊找鬼勒魔。 笑死,一個胖子當(dāng)著我的面吹牛菇曲,可吹牛的內(nèi)容都是我干的冠绢。 我是一名探鬼主播,決...
    沈念sama閱讀 38,271評論 3 399
  • 文/蒼蘭香墨 我猛地睜開眼常潮,長吁一口氣:“原來是場噩夢啊……” “哼唐全!你這毒婦竟也來了?” 一聲冷哼從身側(cè)響起蕊玷,我...
    開封第一講書人閱讀 36,916評論 0 259
  • 序言:老撾萬榮一對情侶失蹤,失蹤者是張志新(化名)和其女友劉穎弥雹,沒想到半個月后垃帅,有當(dāng)?shù)厝嗽跇淞掷锇l(fā)現(xiàn)了一具尸體,經(jīng)...
    沈念sama閱讀 43,382評論 1 300
  • 正文 獨居荒郊野嶺守林人離奇死亡剪勿,尸身上長有42處帶血的膿包…… 初始之章·張勛 以下內(nèi)容為張勛視角 年9月15日...
    茶點故事閱讀 35,877評論 2 323
  • 正文 我和宋清朗相戀三年贸诚,在試婚紗的時候發(fā)現(xiàn)自己被綠了。 大學(xué)時的朋友給我發(fā)了我未婚夫和他白月光在一起吃飯的照片厕吉。...
    茶點故事閱讀 37,989評論 1 333
  • 序言:一個原本活蹦亂跳的男人離奇死亡酱固,死狀恐怖,靈堂內(nèi)的尸體忽然破棺而出头朱,到底是詐尸還是另有隱情运悲,我是刑警寧澤,帶...
    沈念sama閱讀 33,624評論 4 322
  • 正文 年R本政府宣布项钮,位于F島的核電站班眯,受9級特大地震影響,放射性物質(zhì)發(fā)生泄漏烁巫。R本人自食惡果不足惜署隘,卻給世界環(huán)境...
    茶點故事閱讀 39,209評論 3 307
  • 文/蒙蒙 一、第九天 我趴在偏房一處隱蔽的房頂上張望亚隙。 院中可真熱鬧磁餐,春花似錦、人聲如沸阿弃。這莊子的主人今日做“春日...
    開封第一講書人閱讀 30,199評論 0 19
  • 文/蒼蘭香墨 我抬頭看了看天上的太陽渣淳。三九已至畅哑,卻和暖如春,著一層夾襖步出監(jiān)牢的瞬間水由,已是汗流浹背荠呐。 一陣腳步聲響...
    開封第一講書人閱讀 31,418評論 1 260
  • 我被黑心中介騙來泰國打工赛蔫, 沒想到剛下飛機(jī)就差點兒被人妖公主榨干…… 1. 我叫王不留,地道東北人泥张。 一個月前我還...
    沈念sama閱讀 45,401評論 2 352
  • 正文 我出身青樓呵恢,卻偏偏與公主長得像,于是被迫代替她去往敵國和親媚创。 傳聞我的和親對象是個殘疾皇子渗钉,可洞房花燭夜當(dāng)晚...
    茶點故事閱讀 42,700評論 2 345

推薦閱讀更多精彩內(nèi)容