日本搞逼视频_黄色一级片免费在线观看_色99久久_性明星video另类hd_欧美77_综合在线视频

國內最全IT社區平臺 聯系我們 | 收藏本站
阿里云優惠2
您當前位置:首頁 > php開源 > 綜合技術 > Fresco源碼解析 - DataSource怎樣存儲數據

Fresco源碼解析 - DataSource怎樣存儲數據

來源:程序員人生   發布時間:2015-05-26 08:32:42 閱讀次數:3592次

datasource是1個獨立的 package,與FB導入的guava包都在同1個工程內 - fbcore

fbcore的工程結構

datasource的類關系比較簡單,1張類圖基本就能夠描寫清楚它們間的關系。

datasource uml diagram


DataSource 是1個 interface, 功能與JDK中的Future類似,但是相比于Future,它的先進的地方則在于 不單單只生產1個單1的結果,而是能夠提供系列結果

Unlike Futures, DataSource can issue a series of results, rather than just one.

最典型的用處就是漸進式加載圖片時可以提供加載中的中間數據。


DataSubscriberDataSource 構成了1個視察者模式

Datasource 提供了注冊方法。

void subscribe(DataSubscriber<T> dataSubscriber, Executor executor);

通過 subscribe 方法我們可以把 DataSubscriber 注冊成為 DataSource 的視察者,然后當 DataSource 的數據產生變化時,在 Executor 中通知所有的視察者 - DataSubscriber

DataSubscriber 會響應數據的4種變化。

  1. onNewResult
  2. onFailure
  3. onCancellation
  4. onProgressUpdate

使用Executor來通知視察者是比較高明的,這樣做可讓回調方法的履行線程交由 DataSubscriber 來處理,增加了靈活性。


DataSource 只是1個接口,沒有提供任何實現,AbstractDataSource 實現了 DataSource 后封裝了1些基礎的操作,例如 通知視察者記錄數據狀態

Datasource 的狀態記錄使用了1個枚舉類型。

private enum DataSourceStatus { // data source has not finished yet IN_PROGRESS, // data source has finished with success SUCCESS, // data source has finished with failure FAILURE, }

這3種狀態保存在1個成員變量(mDataSourceStatus)中。

@GuardedBy("this") private DataSourceStatus mDataSourceStatus;

AbstractDataSource 構造時,會把 mDataSourceStatus 設置為 IN_PROGRESS

protected AbstractDataSource() { mIsClosed = false; mDataSourceStatus = DataSourceStatus.IN_PROGRESS; mSubscribers = new ConcurrentLinkedQueue<>(); }

所有的視察者(定閱者)會被放在1個列表中 - mSubscribers

private final ConcurrentLinkedQueue<Pair<DataSubscriber<T>, Executor>> mSubscribers;

如果當前的數據要求沒有關閉并且滿足mDataSourceStatus == DataSourceStatus.IN_PROGRESS時才能注冊成功視察者,由于只有當數據產生變化的時候,視察者才有存在的意義。

@Override public void subscribe(final DataSubscriber<T> dataSubscriber, final Executor executor) { Preconditions.checkNotNull(dataSubscriber); Preconditions.checkNotNull(executor); boolean shouldNotify; synchronized(this) { if (mIsClosed) { return; } if (mDataSourceStatus == DataSourceStatus.IN_PROGRESS) { mSubscribers.add(Pair.create(dataSubscriber, executor)); } shouldNotify = hasResult() || isFinished() || wasCancelled(); } if (shouldNotify) { notifyDataSubscriber(dataSubscriber, executor, hasFailed(), wasCancelled()); } }

如果 DataSource 有了新的數據或要求已結束掉或被取消掉,會通知視察者。

private void notifyDataSubscribers() { final boolean isFailure = hasFailed(); final boolean isCancellation = wasCancelled(); for (Pair<DataSubscriber<T>, Executor> pair : mSubscribers) { notifyDataSubscriber(pair.first, pair.second, isFailure, isCancellation); } } private void notifyDataSubscriber( final DataSubscriber<T> dataSubscriber, final Executor executor, final boolean isFailure, final boolean isCancellation) { executor.execute( new Runnable() { @Override public void run() { if (isFailure) { dataSubscriber.onFailure(AbstractDataSource.this); } else if (isCancellation) { dataSubscriber.onCancellation(AbstractDataSource.this); } else { dataSubscriber.onNewResult(AbstractDataSource.this); } } }); }

使用 DataSource 很重要的1點:不要產生內存泄漏,也就是說,用過的資源1定要釋放掉。
使用 DataSubscriber 注冊成了視察者后,回調方法都會帶回1個 DataSource 的實例,如果要求已結束后者失敗了,拿到數據后1定要把 DataSourceclose 掉,否則很容易造成 OOM。

BaseDataSubscriber 就是為了避免OOM,它本身的設計也很奇妙。

在毀掉方法 onNewResultonFailure 中加了1個 try - catch, 在 try 的 block 中調用子類必須重載的 onNewResultImpl 方法,然后在 finally 的 block 中 close DataSource

DataSourceSubscriber.java

public abstract class BaseDataSubscriber<T> implements DataSubscriber<T> { @Override public void onNewResult(DataSource<T> dataSource) { try { onNewResultImpl(dataSource); } finally { if (dataSource.isFinished()) { dataSource.close(); } } } @Override public void onFailure(DataSource<T> dataSource) { try { onFailureImpl(dataSource); } finally { dataSource.close(); } } @Override public void onCancellation(DataSource<T> dataSource) { } @Override public void onProgressUpdate(DataSource<T> dataSource) { } protected abstract void onNewResultImpl(DataSource<T> dataSource); protected abstract void onFailureImpl(DataSource<T> dataSource); }

IncreasingQualityDataSourceSupplierFirstAvailableDataSourceSupplierDataSource 的兩種不同的數據存儲情勢,等后面用到了再做分析。


Supplier 是1個設計比較奇妙的借口,用處非常廣泛。

A class that can supply objects of a single type. Semantically, this could be a factory, generator, builder, closure, or something else entirely. No guarantees are implied by this interface.


SettableDataSourceset 方法中使用 GuavaPreconditions 來做數據合法性檢驗,它與 DataSource 的區分也是僅此而已。

Preconditions

  • checkArgument
  • checkState
  • checkNotNull
  • checkElementIndex
  • checkPositionIndex
  • checkPositionIndexes

如果 check 結果為 false, 則拋出異常。Fresco 的毛病處理基本上是用異常做的。

生活不易,碼農辛苦
如果您覺得本網站對您的學習有所幫助,可以手機掃描二維碼進行捐贈
程序員人生
------分隔線----------------------------
分享到:
------分隔線----------------------------
關閉
程序員人生
主站蜘蛛池模板: 一区二区三区四区在线 | 亚洲精品国产第一综合99久久 | 久久久久久久久久国产 | 国产一区在线免费观看 | 国产欧美日韩综合精品一区二区 | 日韩中文字幕一区二区三区 | 九九九九久久久久 | 噢美一级片| 黄a视频| 综合导航 | 成人午夜精品 | 精品999在线观看 | 超碰免费在线观看 | 日韩二区三区 | 免费福利视频一区二区三区 | 不卡欧美| 久久久99国产精品免费 | 中文字幕在线观看日本 | 亚洲视频免费观看 | 精品国产黄色片 | 欧美精品一区在线观看 | 欧美日本韩国 | 亚洲视频免费观看 | 99精品在线观看 | 黄色小视频在线免费观看 | 国产二区久久 | 久久免费观看少妇a级毛片 亚洲成人一区二区 | 国产男女视频 | 久久久久久免费毛片精品 | 福利视频在线播放 | 成人精品视频在线观看 | 久久成人综合 | 国产成人综合自拍 | 国产精品久久久久久 | 精品国产青草久久久久福利 | 婷久久 | 色就是色欧美亚洲 | 亚洲不卡视频 | 国产精品久久久久7777按摩 | 欧美日韩一区在线观看 | 精品视频免费 |