Android原始碼設計模式-模板模式

jamesehng發表於2018-07-01

模板模式

模板模式在Android原始碼中出現的很多,比如Activity和Srervice的生命週期,啟動過程,還有AsyncTask類等。模板模式可以理解為一種演算法流程的集合,可以通過建構函式來靈活控制流程,實現抽象方法,來具體化細節。

使用

1.具有相似流程的演算法,可以考慮抽象出模板。 2.在重構過程中,可以把相似的子類抽象出一個模板父類,比如我們Android的BaseActivity和BaseAdapter等抽象類。

官方定義

定義一個操作中演算法的骨架,而將一些步驟延遲到子類中,模板方法使得子類可以不改變演算法的結構即可重定義該演算法的某些特定步驟。

通俗點的理解就是 :完成一件事情,有固定的數個步驟,但是每個步驟根據物件的不同,而實現細節不同;就可以在父類中定義一個完成該事情的總方法,按照完成事件需要的步驟去呼叫其每個步驟的實現方法。每個步驟的具體實現,由子類完成。

結構

1.抽象父類 2.具體的子類

Android原始碼設計模式-模板模式

優缺點

模板模式的優點

 (1)具體細節步驟實現定義在子類中,子類定義詳細處理演算法是不會改變演算法整體結構。

 (2)程式碼複用的基本技術,在資料庫設計中尤為重要。

 (3)存在一種反向的控制結構,通過一個父類呼叫其子類的操作,通過子類對父類進行擴充套件增加新的行為,符合“開閉原則”。

缺點

每個不同的實現都需要定義一個子類,會導致類的個數增加,系統更加龐大。

在Android原始碼中的使用

1.系統啟動過程,具體參考這篇部落格: https://juejin.im/post/5b3885d96fb9a00e687a0708 2.元件生命週期,比如Activity和Service等 3.一些具體封裝類,比如AsyncTask等

舉例AsyncTask Android原始碼

首先眾所周知,AsyncTask的模板就是那幾個抽象方法,等你去實現,我們每次使用這個類,就是實現一個具體的子類,而且一個物件只能用一次,為什麼呢?我們下面一一解開

模板

1.onPreExecute() 2.doInBackground() 3.onProgressUpdate() 4.onPostExecute()

抽象父類的細節

首先介紹幾個角色: 1.ThreadPool:AsyncTask預設用執行緒池來切換執行緒,這個執行緒池在不通Android版本是不一樣的,最初始序列的,後來是並行,現在又是序列,是一個全域性的執行緒池。

2.Handler:這個用於執行緒的訊息互動,主要是子執行緒通知到UI執行緒,因為onPostEx'ecute()是在UI執行緒,所以我們handler必須在U執行緒初始化。

為什麼AsyncTask必須在UI執行緒初始化呢?

就是以為內部的Handler必須是繫結UI執行緒的,而這個handler繫結的執行緒是也是在AsyncTask初始化的當前執行緒。

介紹模板呼叫細節

1.首先執行AsyncTask.Execute(Params)

這個方法會呼叫ExecuteOnExecutor(Executor,Params),會傳入預設的執行緒池:sDefaultExecutor和引數

2.ExecuteOnExecutor(Executor,Params)

這個方法會做以下幾件事: 1.開始判斷AsyncTask物件是否處於Running和Finish狀態,如果是就會彈出異常。然後設定這個AsyncTask物件處於running狀態。這也是為什麼一個AsyncTask物件只能用一次。

2.呼叫onPreExecute()做一些初始化和準備。

3.呼叫doInBackground,初始化mWorker,並把Params賦值給mWorker的mParams成員。mWorker實現了Callable介面並在視線中呼叫了postResult(doInBackground(Params)),這個方法是關鍵,完成了執行緒切換,我們後面展開講。

4.初始化mFuture,這是一個FutureTask物件,可以理解為一個Thread物件。

5.sDefaultExecutor.execute(mFuture),mFuture的run()方法會呼叫mWorker的call回撥方法,最終呼叫postResult(doInBackground(Params))

postResult(doInBackground(Params))方法

以上是onPreExecute()和doInBackground()方法已經被呼叫了

postResult(doInBackground(Params))這個方法做了一下幾個事: 1.構造一個AsyncTaskResult,這個物件是兩個物件構造: AsyncTask物件例項 doInBackground執行完的Result

2.構造一個UI執行緒Handler的Message,what是MESSAGE_POST_RESULT,obj是AsyncTaskResult

3.傳送給UI執行緒Handler處理。這個handler能處理兩類訊息就是: MESSAGE_POST_RESULT:收到這個訊息後切換到UI執行緒,取出obj裡面的AsyncTask物件例項呼叫finish()方法,finish方法會呼叫onPostExecute()犯法,並且把狀態標為finish。 MESSAGE_POST_PROGRESS訊息: 會呼叫AsyncTask物件例項的onUpdateProgress()方法

結束

模板模式在Android原始碼架構層面也處處可見,如果你留意就會經常發現它的身影。

相關文章