protobuf的使用

使用protobuf有一段時間,沒有做記錄。在android系統中使用時出現了找不到方法,才認真研究了一下。就做了一起大概的記錄。

一、安裝java環境和NDK環境(不多說,自己準備)

二、下載protobuf代碼http://code.google.com/p/protobuf/downloads/list 

三、如果第二步自己編譯了,這步就不用做。

1,下載protobuf-win32.zip

2,下載protobuf.jar(http://code.google.com/p/android-market-api/downloads/detail?name=protobuf-java-2.2.0.jar&can=2&q=

四、編譯.proto爲java類

protoc --java_out=src Person.proto

本命令將Pserson.proto 編譯成Person.java類,在java項目中可以直接使用,當然要加下三2步的jar包

五、編寫.proto文件

選項:option

1,java_package (file option): 這個選項表明生成java類所在的包。如果在.proto文件中沒有明確的聲明java_package,就採用默認的包名。當然了,默認方式產生的 java包名並不是最好的方式,按照應用名稱倒序方式進行排序的。如果不需要產生java代碼,則該選項將不起任何作用。如:

option java_package = "com.example.foo";

2,java_outer_classname (file option): 該選項表明想要生成Java類的名稱。如果在.proto文件中沒有明確的java_outer_classname定義,生成的class名稱將會根據.proto文件的名稱採用駝峯式的命名方式進行生成。如(foo_bar.proto生成的java類名爲FooBar.java),如果不生成java代碼,則該選項不起任何作用。如:

option java_outer_classname = "Ponycopter";

3,optimize_for (fileoption): 可以被設置爲 SPEED, CODE_SIZE,or LITE_RUNTIME。這些值將通過如下的方式影響C++及java代碼的生成:

· SPEED (default): protocol buffer編譯器將通過在消息類型上執行序列化、語法分析及其他通用的操作。這種代碼是最優的。

· CODE_SIZE: protocol buffer編譯器將會產生最少量的類,通過共享或基於反射的代碼來實現序列化、語法分析及各種其它操作。採用該方式產生的代碼將比SPEED要少得多, 但是操作要相對慢些。當然實現的類及其對外的API與SPEED模式都是一樣的。這種方式經常用在一些包含大量的.proto文件而且並不盲目追求速度的 應用中。

· LITE_RUNTIME: protocol buffer編譯器依賴於運行時核心類庫來生成代碼(即採用libprotobuf-lite 替代libprotobuf)。這種核心類庫由於忽略了一 些描述符及反射,要比全類庫小得多。這種模式經常在移動手機平臺應用多一些。編譯器採用該模式產生的方法實現與SPEED模式不相上下,產生的類通過實現 MessageLite接口,但它僅僅是Messager接口的一個子集。

option optimize_for = CODE_SIZE;

4,cc_generic_servicesjava_generic_servicespy_generic_services (file options): 在C++、java、python中protocol buffer編譯器是否應該基於服務定義產生抽象服務代碼。由於歷史遺留問題,該值默認是true。但是自2.3.0版本以來,它被認爲通過提供代碼生成 器插件來對RPC實現更可取,而不是依賴於“抽象”服務。

// This file relies on plugins to generate service code.
option cc_generic_services = false;
option java_generic_services = false;
option py_generic_services = false;

5,message_set_wire_format (message option):如果該值被設置爲true,該消息將使用一種不同的二進制格式來與Google內部的MessageSet的老格式相兼容。對於Google外部的用戶來說,該選項將不會被用到。如下所示:

message Foo {
  option message_set_wire_format = true;
  extensions 4 to max;
}

6,packed (field option): 如果該選項在一個整型基本類型上被設置爲真,則採用更緊湊的編碼方式。當然使用該值並不會對數值造成任何損失。在2.3.0版本之前,解析器將會忽略那些 非期望的包裝值。因此,它不可能在不破壞現有框架的兼容性上而改變壓縮格式。在2.3.0之後,這種改變將是安全的,解析器能夠接受上述兩種格式,但是在 處理protobuf老版本程序時,還是要多留意一下。

repeated int32 samples = 4 [packed=true];

7,deprecated (field option): 如果該選項被設置爲true,表明該字段已經被棄用了,在新代碼中不建議使用。在多數語言中,這並沒有實際的含義。在java中,它將會變成一個 @Deprecated註釋。也許在將來,其它基於語言聲明的代碼在生成時也會如此使用,當使用該字段時,編譯器將自動報警。如:

optional int32 old_field = 6 [deprecated=true];

自定義選項

ProtocolBuffers允許自定義並使用選項。該功能應該屬於一個高級特性,對於大部分人是用不到的。由於options是定在 google/protobuf/descriptor.proto中的,因此你可以在該文件中進行擴展,定義自己的選項。

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章