在Android中使用FlatBuffers - 简介
JSON - 可能每個人都知道這個輕量的數(shù)據(jù)格式幾乎被用在了所有的現(xiàn)代服務(wù)器中。相對于過去流行的一些東西,如可怕的XML,它更輕量,更可讀,對開發(fā)更友好。JSON是語言獨立的數(shù)據(jù)格式,但解析和格式轉(zhuǎn)化,比如轉(zhuǎn)為Java對象,耗費了我們的時間和內(nèi)存資源。
幾天以前,Facebook宣布,在它的Android app中的數(shù)據(jù)處理部分獲得了巨大的性能提升。那與 幾乎在整個app中丟棄JSON格式,而用FlatBuffers代替有關(guān)。請參考這篇文章來了解一些關(guān)于FlatBuffers的基本知識,以及從JSON轉(zhuǎn)換到它的結(jié)果。
盡管結(jié)果看上去非常好,但乍一看實現(xiàn)方式不是特別明顯。Facebook也沒有說太多。那也就是為什么我想在這篇文章中展示我們可以如何使用FlatBuffers。
FlatBuffers
簡單地說,FlatBuffers是Google的一個跨平臺序列化庫,特別為游戲開發(fā)創(chuàng)建以及,如Facebook所展示的那樣,遵循Android中的流暢的及響應(yīng)式UI的16ms規(guī)則。
但是注意了,在你扔掉一切,將你的所有數(shù)據(jù)遷移到FlatBuffers之前,請先確認你需要這樣做。有時候?qū)π阅艿挠绊憣⑹菢O其微小的,而有時候數(shù)據(jù)安全性比計算速度上幾十毫秒的差異重要得多。
什么使FlatBuffers如此高效?
- 由于平坦的二進制緩沖區(qū),訪問序列化后的數(shù)據(jù)時無需解析,即使是對于層次式的數(shù)據(jù)。多虧于這一點,我們不需要初始化解析器(這意味著構(gòu)造復(fù)雜的字段映射),以及解析數(shù)據(jù),這也耗費時間。
- FlatBuffers數(shù)據(jù)不需要分配多于緩沖區(qū)本身所用大小的內(nèi)存。我們不需要像在JSON中那樣,為解析后的層次式數(shù)據(jù)分配額外的對象。
要獲取真實的數(shù)字可以參考關(guān)于向FlatBuffers遷移的facebook的文章,或者Google文檔。
實現(xiàn)
這篇文章將描述在Android app中使用FlatBuffers的最簡單的方式:
- 在app之外的某個地方將JSON數(shù)據(jù)轉(zhuǎn)換為FlatBUffers格式(比如將二進制文件以文件的形式傳送,或直接從API返回)。
- 通過flatc (FlatBuffer編譯器) 手動產(chǎn)生數(shù)據(jù)模型(Java 類)。
- JSON文件有一些限制 (不能使用null字段,Data格式被解析為一個String)。
可能在未來我們將準備更復(fù)雜的方案。
FlatBuffers編譯器
首先我們要先獲取flatc - FlatBuffers編譯器。它可以通過位于Google的flatbuffers倉庫中的源代碼來構(gòu)建。讓我們下載/clone它。整個的構(gòu)建過程在FlatBuffers構(gòu)建文檔中描述。如果你是Mac用戶則你需要做的是:
現(xiàn)在我們可以使用schema編譯器(以Java,C#,Python,GO和C++語言)來為給定的模式產(chǎn)生模型類,以及將JSON轉(zhuǎn)換為FlatBuffer二進制文件了。
模式文件
現(xiàn)在我們必須要準備模式文件了,它定義了我們想要 反-/序列化 的數(shù)據(jù)結(jié)構(gòu)。這個模式將被flatc用于創(chuàng)建Java模型以及從JSON到FlatBuffer二進制文件的轉(zhuǎn)換。
這是我們的JSON文件的一部分:
{"repos": [{"id": 27149168,"name": "acai","full_name": "google/acai","owner": {"login": "google","id": 1342004,..."type": "Organization","site_admin": false},"private": false,"html_url": "https://github.com/google/acai","description": "Testing library for JUnit4 and Guice.",..."watchers": 21,"default_branch": "master"},...] }repos_json_fragment.json 位于GitHub
可以在這里獲取完整的版本。它是通過調(diào)用如下的Github API所獲數(shù)據(jù)經(jīng)過了一點修改的版本:
https://api.github.com/users/google/repos.
編寫FlatBuffer模式文件的文檔非常好,因而在這里我就不再深入說明了。在我們的例子中模式文件也不是非常復(fù)雜。我們所要做的所有事情就是創(chuàng)建3個表:ReposList,Repo和User,并定義root_type。下面是這個模式文件的重要部分:
table ReposList {repos : [Repo]; }table Repo {id : long;name : string;full_name : string;owner : User;//...labels_url : string (deprecated);releases_url : string (deprecated); }table User {login : string;id : long;avatar_url : string;gravatar_id : string;//...site_admin : bool; }root_type ReposList;repos_schema_fragment.fbs 位于GitHub
完整的模式文件在這里。
FlatBuffers數(shù)據(jù)文件
很好,現(xiàn)在我們所需要做的就是將repos_json.json轉(zhuǎn)換為FlatBuffers二進制文件,并產(chǎn)生Java模型,其可以以Java友好的方式表示我們的數(shù)據(jù)(這個操作所需的所有的所有文件可以在我們的repository獲取):
$ ./flatc -j -b repos_schema.fbs repos_json.json如果一切順利,這將產(chǎn)生如下的文件:
- repos_json.bin (將被重命名為repos_flat.bin)
- Repos/Repo.java
- Repos/ReposList.java
- Repos/User.java
Android app
現(xiàn)在讓我們來創(chuàng)建我們的示例app,來看下FlatBuffers格式是如何在實際中使用的。這是它的截屏:
screenshot.png
ProgressBar將僅被用于展示不正確的數(shù)據(jù)處理(在UI線程中)可以如何影響用戶界面的流暢度。
我們的app的app/build.gradle文件看起來如下面這樣:
apply plugin: 'com.android.application' apply plugin: 'com.jakewharton.hugo'android {compileSdkVersion 22buildToolsVersion "23.0.0 rc2"defaultConfig {applicationId "frogermcs.io.flatbuffs"minSdkVersion 15targetSdkVersion 22versionCode 1versionName "1.0"}buildTypes {release {minifyEnabled falseproguardFiles getDefaultProguardFile('proguard-android.txt'), 'proguard-rules.pro'}} }dependencies {compile fileTree(dir: 'libs', include: ['*.jar'])compile 'com.android.support:appcompat-v7:22.2.1'compile 'com.google.code.gson:gson:2.3.1'compile 'com.jakewharton:butterknife:7.0.1'compile 'io.reactivex:rxjava:1.0.10'compile 'io.reactivex:rxandroid:1.0.0' }當然,在我們的例子中沒必要使用Rx或ButterKnife,但為什么不讓這個app更好一點呢
總結(jié)
以上是生活随笔為你收集整理的在Android中使用FlatBuffers - 简介的全部內(nèi)容,希望文章能夠幫你解決所遇到的問題。
- 上一篇: 懒人chromium net andro
- 下一篇: 用FlatBuffers提升Androi