android.support.v4.util.Pools原始碼解析
簡述:
今天看別人程式碼,突然發現一個類pools,然後點進去看發現是在v4包下的一個工具類。官方文件對其介紹比較簡單就一句話:
Helper class for crating pools of objects.
物件池存取的輔助類。OK,接下來我們就分析一下原始碼然後再來研究一下它的使用。
原始碼分析:
由於原始碼不多,所以直接貼出來便於分析:
public final class Pools { /** * Interface for managing a pool of objects. * * @param <T> The pooled type. */ public static interface Pool<T> { /** * @return An instance from the pool if such, null otherwise. */ public T acquire(); /** * Release an instance to the pool. * * @param instance The instance to release. * @return Whether the instance was put in the pool. * * @throws IllegalStateException If the instance is already in the pool. */ public boolean release(T instance); } private Pools() { /* do nothing - hiding constructor */ } /** * Simple (non-synchronized) pool of objects. * * @param <T> The pooled type. */ public static class SimplePool<T> implements Pool<T> { private final Object[] mPool; private int mPoolSize; /** * Creates a new instance. * * @param maxPoolSize The max pool size. * * @throws IllegalArgumentException If the max pool size is less than zero. */ public SimplePool(int maxPoolSize) { if (maxPoolSize <= 0) { throw new IllegalArgumentException("The max pool size must be > 0"); } mPool = new Object[maxPoolSize]; } @Override @SuppressWarnings("unchecked") public T acquire() { if (mPoolSize > 0) { final int lastPooledIndex = mPoolSize - 1; T instance = (T) mPool[lastPooledIndex]; mPool[lastPooledIndex] = null; mPoolSize--; return instance; } return null; } @Override public boolean release(T instance) { if (isInPool(instance)) { throw new IllegalStateException("Already in the pool!"); } if (mPoolSize < mPool.length) { mPool[mPoolSize] = instance; mPoolSize++; return true; } return false; } private boolean isInPool(T instance) { for (int i = 0; i < mPoolSize; i++) { if (mPool[i] == instance) { return true; } } return false; } } /** * Synchronized) pool of objects. * * @param <T> The pooled type. */ public static class SynchronizedPool<T> extends SimplePool<T> { private final Object mLock = new Object(); /** * Creates a new instance. * * @param maxPoolSize The max pool size. * * @throws IllegalArgumentException If the max pool size is less than zero. */ public SynchronizedPool(int maxPoolSize) { super(maxPoolSize); } @Override public T acquire() { synchronized (mLock) { return super.acquire(); } } @Override public boolean release(T element) { synchronized (mLock) { return super.release(element); } } } }
從上面的原始碼中可以看出:這個工具類中包含一個私有的構造方法、一個介面和兩個類,下面詳細解析一下:
1、Pools類中僅且僅有一個方法,而且該方法為一個私有的構造方法:於是Pools類不能夠直接被使用,只能使用其子類(可以預測其一定而且必須有子類)。
2、包含一個介面Pool<T>,該介面中包含兩個方法:
T acquire():獲取一個T物件。
boolean release(T element):向物件池中新增一個物件,如果該物件已存在於物件池中,則丟擲異常IllegalStateException。返回true表示新增成功,否則失敗。
3、包含兩個類:SimplePool<T> 和 SynchronizedPool<T>:
SimplePool<T>實現了Pool介面:其內部利用一個Object[ ]陣列來維護這個物件池。
SynchronizedPool<T>:其繼承於SimplePool,是對SimplePool的進一步封裝,簡單地說就是對每個方法加了一個同步鎖。
OK,分析就分析到這裡,接下來我們來看其使用。
使用說明:
我們約定接下來的幾個例子當中物件池中儲存的物件DataSet定義如下:
import java.util.HashMap; /** * @author lizhenya * @description 資料集合,支援傳遞複雜資料 * @since 12/11/2015 */ public class DataSet { private HashMap<Object, Object> data = new HashMap<Object, Object>(); private Object reciver; public Object getReciver() { return reciver; } public void setReciver(Object reciver) { this.reciver = reciver; } public void put(Object key, Object value) { data.put(key, value); } @SuppressWarnings("unchecked") public <T> T get(Class<T> cls, String key) { Object obj = data.get(key); if (obj != null && (obj.getClass() == cls || cls.isInstance(obj))) return (T) obj; return null; } public Object get(String key) { return data.get(key); } public void recycle() { reciver = null; data.clear(); } public String getString(String key) { String result = get(String.class, key); return result == null ? null : result; } public int getInt(String key) { Integer result = get(Integer.class, key); return result == null ? 0 : result; } public int getInt(String key, int defaultVal) { Integer result = get(Integer.class, key); return result == null ? defaultVal : result; } public float getFloat(String key) { Float result = get(Float.class, key); return result == null ? 0 : result; } public float getFloat(String key, float defaultVal) { Float result = get(Float.class, key); return result == null ? defaultVal : result; } public long getLong(String key) { Long result = get(Long.class, key); return result == null ? 0 : result; } public boolean getBoolean(String key) { Boolean result = get(Boolean.class, key); return result == null ? false : result; } public String[] getStringArray(String key) { String[] array = get(String[].class, key); return array == null ? null : array; } }
1、使用SimplePool來維護一個物件池
/**
* @author:lizhenya
* @Time: 16/10/24
* @email: [email protected]
*/
public class DataPool extends Pools.SimplePool<DataSet> {
/**
* Creates a new instance.
*
* @param maxPoolSize The max pool size.
* @throws IllegalArgumentException If the max pool size is less than zero.
*/
public DataPool(int maxPoolSize) {
super(maxPoolSize);
}
/**
* 方法描述:獲取DataSet物件
*
* @return
*/
public DataSet get() {
return acquire() != null ? acquire() : new com.lzy.poolsdemo.DataSet();
}
/**
* 方法描述:判斷物件池中是否包含dataSet物件例項
*
* @param dataSet DataSet物件
* @return 如果包含含dataSet物件例項返回true, 如果不包含則將dataset物件例項新增到物件池並返回false
*/
public boolean obtain(DataSet dataSet) {
return release(dataSet);
}
}
2、ListPools
在SimplePools中物件的維護使用的是陣列,陣列有個最大的缺點:儲存滿了後不能自增長。所以既要保證效率又能自增長可以採用ArrayList來維護該物件池,下面我們自定義一個ListPool:
/**
* @author:lizhenya
* @Time: 16/10/24
* @email: [email protected]
*/
public class ListPool<T> implements Pools.Pool<T> {
/**
* 同步ArrayList
**/
private final List<T> ts;
public ListPool(int maxPoolSize) {
ts = Collections.synchronizedList(new ArrayList<T>(maxPoolSize));
}
@Override
public T acquire() {
if (ts.isEmpty())
return null;
return ts.remove(0);
}
@Override
public boolean release(T instance) {
return ts.add(instance);
}
}
使用如下:
/**
* @author:lizhenya
* @Time: 16/10/24
* @email: [email protected]
*/
public class ListDataPools extends ListPool<DataSet> {
public ListDataPools(int maxPoolSize) {
super(maxPoolSize);
}
public DataSet get() {
return acquire() == null ? new DataSet() : acquire();
}
public boolean obtain(DataSet dataSet) {
dataSet.recycle();
return release(dataSet);
}
}
OK,關於android.support.v4.util.Pools的使用與解析比較簡單,到此結束。再有半個小時1024程式設計師節日就要結束了,對大家也對自己說聲“節日快樂”。
相關推薦
android.support.v4.util.Pools原始碼解析
簡述: 今天看別人程式碼,突然發現一個類pools,然後點進去看發現是在v4包下的一個工具類。官方文件對其介紹比較簡單就一句話: Helper class for crating pools of objects. 物件池存取的輔助類。OK,接下來
android.support.v4.util.Pool 類解析
今天閒著沒事看看 android v4包,結果發現一個類Pools.java,看了一下,從字面上的意思來看應該也是池,我自然而然的就會聯想到執行緒池,看了一下,Pools類其實是物件池 裡面維護了一個數組,廢話不多說,看程式碼: public final class Poo
android.support.v4.app.Fragment原始碼解析
Fragment最基礎功能使用 FragmentManager fm=getFragmentManager(); FragmentTransaction transaction=fm.beginTransaction(); mFirstFragment
android-support-v4.jar 關聯原始碼
1. 在 libs 資料夾下,新建名為 “android-support-v4.jar.properties” 的配置檔案。 2. 編輯該檔案,新增內容 src=C:\Software\android-sdks\extras\android\support\v4\src 3. 將該工程關閉,再次開啟即可
兔子--Android Support v4包丟失的解決的方法
external extern add ras build -a post -- ont 在開發中,Android Support v4包丟失的解決的方法: Project->properties->Java Build Path->Librari
Cannot resolve symbol KeyEventCompat(android.support.v4.view.KeyEventCompat找不到)
blog forward CA res tco sdn hand andro exe Cannot resolve symbol KeyEventCompat(android.support.v4.view.KeyEventCompat找不到) 解決方案 KeyEventC
Error inflating class android.support.v4.view.ViewaPager解決辦法 Android studio版本
點選依賴管理 切換到依賴 點選加號 搜尋v4點選新增 發現找不到一部分資原始檔 ,因為版本不符合 在我們的gradle檔案中修改版本號 我這裡是26的編譯版本所以改為26 ok編譯通過 &
讓Android Support V4中的SwipeRefreshLayout支援上拉載入更多
分享一下我老師大神的人工智慧教程!零基礎,通俗易懂!http://blog.csdn.net/jiangjunshow 也歡迎大家轉載本篇文章。分享知識,造福人民,實現我們中華民族偉大復興!  
Android之帶你從原始碼解析Bitmap佔用記憶體正確的計算公式
Bitmap 前言 Bitmap簡介 畫素儲存方式 圖片壓縮格式 Bitmap記憶體計算 釋放記憶體 獲取Bitmap所佔記憶體 計算所佔記憶體 舉例 Bitmap.getAllo
android面試——開源框架的原始碼解析
1、EventBus (1)通過註解+反射來進行方法的獲取 註解的使用:@Retention(RetentionPolicy.RUNTIME)表示此註解在執行期可知,否則使用CLASS或者SOURCE在執行期間會被丟棄。 通過反射來獲取類和方法:因為對映關係實際上是類對映到所有此類
android-support-v4.jar 在匯入其他 library 時衝突
錯誤場景 我出現這個問題是在做側邊欄時匯入SlidingMenu的library時出現v4包時衝突 錯誤原因 這是
Found 2 versions of android-support-v4.jar in the dependency list,The type android.support.v4.app.Fr
1、 Found 2 versions of android-support-v4.jar in the dependency list, but not all the versions are identical (check is based on SHA-1 only at t
android support-v4包找不到依賴
問題:編譯報錯Error:Failed to resolve: com.android.support:support-core-ui:23.4.0 解決:嘗試了很多方法比如gradle檔案中加入如下域名 allprojects { repositories {
android-support-v4
android support v4 26.0.0-alpha1分包下載地址 support-annotations-26.0.0-alpha1.jar http://download.csdn.net/detail/lmjssjj/9903787 android-support
Error: Program type already present: android.support.v4.app.FragmentTransitionCompat21$1
參考連結 https://stackoverflow.com/questions/52845161/error-program-type-already-present-android-support-v4-app-fragmenttransitionco 主要原因: gra
android.support.v4.app.backstackrecord$Op
Program type already present:android.support.v4.app.backstackrecord$Op (程式型別已經存在:android.support.v4.app.backstackrecord$Op) 本來專案好好的。。過了幾天執行就起不來了。。
【Android P】 JobScheduler服務原始碼解析(二) ——服務端啟動解析
JoScheduler服務框架分析 App端從建立一個job 到排程一個Job流程是怎樣的? Job在App端主要比較重要的類有四個:JobInfo,JobScheduler,JobService,JobServiceEngine public class Jo
(Android)為什麼我們不需要匯入android support v4包?
開發中發現了一個奇怪的問題,在沒有引入support v4包的情況下,卻可以用support v4路徑下的Fragment。於是看了一下Android Studio左側的External Libaries依賴樹,發現已經包含了support v4的包,而且其中還
Error: Program type already present: android.support.v4.accessibilityservice.AccessibilityServiceInf
報錯原因:v4包衝突 配置ButterKnife過程中報錯(與support-v4包衝突,Program type already present: android.support.v4..) 解決 上github上原始碼那裡查了一下,在根目錄的build.gradle可以看到
【Android 開發】: Android 訊息處理機制之四: Android 訊息迴圈 Looper 及其原始碼解析
上一講我們學習Handler和Message的一些使用方式,我們知道Handler它會發送訊息和處理訊息,並且關聯一個子執行緒,如何傳送訊息入隊和出隊處理訊息等這些都是交給Looper去管理分發的,也就是它是負責整個訊息佇列運轉的一個類,這一講我們就來學習一下Andr