編輯:關於Android編程

這些類的繼承關系如下圖所示:<喎?/kf/ware/vc/" target="_blank" class="keylink">vcD4KPHA+PGltZyBzcmM9"/uploadfile/Collfiles/20140711/20140711090242214.jpg" alt="\">
如同文件緩存一樣,內存緩存涉及的接口也有兩個:MemoryCacheAware 和MemoryCache,其中MemoryCache只是簡單的繼承了MemoryCacheAware並沒有聲明其他的方法。MemoryCacheAware接口的方法如下:
@Deprecated public interface MemoryCacheAware{ /** *根據key值把value放入緩存 * @return 如果放入緩存成功的話就返回true,反之返回false */ boolean put(K key, V value); /**根據key從緩存中獲取數據,沒有相關數據則返回null*/ V get(K key); /** 根據key從緩存中刪除數據*/ void remove(K key); /** 返回緩存中所有的key */ Collection keys(); /** 清空緩存*/ void clear(); }
BaseMemoryCache:
該類是一個抽象類,提供了一個map,用來緩存Bitmap的弱引用:
private final Map> softMap = Collections.synchronizedMap(new HashMap >());
/**根據value創建一個弱引用對象,該類為抽象類,供子類實現 */ protected abstract ReferencecreateReference(Bitmap value); @Override public boolean put(String key, Bitmap value) { softMap.put(key, createReference(value)); return true; }
LimitedMemoryCache:
該類為抽象類,繼承了BaseMemoryChache;對緩存進行了兩個限制:1) 限制每一個緩存圖片的最大值:用sizeLimit來作為標致,對大於sizeLimit大小的bitmap對象,調用父類的put方法保存bitmap的弱引用。否則在保存弱引用的同時,把Bitmap對象的強引用用類型為LinkedList變量hardCache緩存起來,
2) 同樣用sizeLimit來限制整個緩存的大小。對是否超出緩存大小的限制在put方法被調用的時候會做判斷,如果緩存大小超出限制就從LinkedList中刪除對應的bitmap對象,具體的刪除策略有該類的抽象方法remoeNext()提供,具體的在子父類中實現(比如有的是刪除最大的那個bitMap,以及根據FIFO算法刪除等等),這是典型的模板方法模式的應用。具體的模板方法為romoveNext()和getSize()由相應的子類實現。
注意put方法的返回值,當要加入的bitMap的大小超過sizeLimit的就返回false,否則返回true(在子類中調用該put方法,返回true說明對緩存進行了對應的刪除操作)
private final ListhardCache = Collections.synchronizedList(new LinkedList ());//hardCache只是在此類中只是用來對緩存是否超過sizeLimit做判斷。 //bitMap放入緩存 @Override public boolean put(String key, Bitmap value) { boolean putSuccessfully = false; // Try to add value to hard cache //getSize方法為抽象方法,由子類實現 int valueSize = getSize(value); int sizeLimit = this.sizeLimit; int curCacheSize = cacheSize.get(); //當bitmap的大小小於sizeLimit的大小時 if (valueSize < sizeLimit) { //對緩存進行刪除操作,使之不超過siezeLimit的限制,。我們 while (curCacheSize + valueSize > sizeLimit) { Bitmap removedValue = removeNext();//removeNext()為抽象方法,由不同的子類提供不同的刪除策略 if (hardCache.remove(removedValue)) { curCacheSize = cacheSize.addAndGet(-getSize(removedValue)); } } //放入緩存 hardCache.add(value); //設置緩存大小 cacheSize.addAndGet(valueSize); putSuccessfully = true; } //獲取bitMap的大小 protected abstract int getSize(Bitmap value); //模板方法,由相應的子類來實現具體的刪除策略 protected abstract Bitmap removeNext();
該類為LimitedMemoryCache的子類,該類的目的是當超出緩存大小限制的時候刪除緩存中最大的那個bitmap對象。該類實現了父類的兩個抽象方法:getSize()和removeNext()來獲取某個bitmap的大小和刪除最大的那個bitMap對象。
實現的原理: 該類添加了一個map變量,該map的key用來保存bitMap對象,而對應的value則保存bitmap的大小。
private final MapvalueSizes = Collections.synchronizedMap(new HashMap ());
/**
* 循環遍歷valueSizes,並獲取最大的那個bitmap,並且從map中刪除之
返回的Bimmap對象交給父類的hardCache刪除
*/
@Override
protected Bitmap removeNext() {
Integer maxSize = null;
Bitmap largestValue = null;
Set> entries = valueSizes.entrySet();
synchronized (valueSizes) {
for (Entry entry : entries) {
if (largestValue == null) {
largestValue = entry.getKey();
maxSize = entry.getValue();
} else {
Integer size = entry.getValue();
if (size > maxSize) {
maxSize = size;
largestValue = entry.getKey();
}
}
}
}
//執行刪除稻作
valueSizes.remove(largestValue);
return largestValue;
}
//獲取getSize的方法
@Override
protected int getSize(Bitmap value) {
return value.getRowBytes() * value.getHeight();
}
@Override
protected Reference createReference(Bitmap value) {
return new WeakReference(value);
}
刪除操作執行時機:調用父類put方法是執行
@Override
public boolean put(String key, Bitmap value) {
if (super.put(key, value)) {//如果父類的方法為空,說明緩存的大小沒有超出限制
valueSizes.put(value, getSize(value));
return true;
} else {//緩存的大小超出限制
return false;
}
}FIFOLimitedMemoryCache :
LimitedMomroyCache的子類,當當前緩存的大小超出限制的時候,會根據FIFO(先進先出)算法刪除響應的bitmap緩存對象。該類用LinkedList來作為FIFO的實現方式,當超出緩存大小的時候,調用removeNext()來從緩存中刪除首先加入進來的bitmap對象。相應的方法如下:
實現原理:提供了一個LinkedList來保存bitmap對象
private final Listqueue = Collections.synchronizedList(new LinkedList ());
@Override
protected Bitmap removeNext() {
return queue.remove(0);
}
@Override
protected Reference createReference(Bitmap value) {
return new WeakReference(value);
}
@Override
protected int getSize(Bitmap value) {
return value.getRowBytes() * value.getHeight();
} 刪除操作執行時機:調用父類put方法是執行
@Override
public boolean put(String key, Bitmap value) {
if (super.put(key, value)) {//如果緩存沒有超出范圍
queue.add(value);//把bitmap放入隊列
return true;
} else {//緩存超出范圍
return false;
}
}LRULimitedMemoryCache:
LimitedMemoryCache的子類,最近最久未使用緩存,當緩存大小超過sizeLimit限制的時候,就從緩存中刪除最近最久未使用的bitmap緩存對象。實現原理:提供了一個LinkedHashMap來保存對象,實現LRU的效果
/** Cache providing Least-Recently-Used logic */ private final Map具體的removeNext()方法實現:lruCache = Collections.synchronizedMap(new LinkedHashMap (INITIAL_CAPACITY, LOAD_FACTOR, true));
@Override
protected Bitmap removeNext() {
return queue.remove(0);
}
@Override
protected Reference createReference(Bitmap value) {
return new WeakReference(value);
}
@Override
protected int getSize(Bitmap value) {
return value.getRowBytes() * value.getHeight();
} @Override
public boolean put(String key, Bitmap value) {
if (super.put(key, value)) {//如果緩存沒有超出范圍
queue.add(value);//把bitmap放入隊列
return true;
} else {//緩存超出范圍
return false;
}
}
UsingFreqLimitedMemoryCache:
LimitedMemoryCache的子類,當緩存大小超出sizelimit的時候對最久未使用的bitmap對象進行刪除(也就是說對使用次數最少的那個bitmap進行刪除操作)
實現原理:提供了一個hashMap,該map的key保存bitmap對象,而value則保存對應bitmap的使用次數
private final Map當調用get(string key)方法獲取bitmap的時候,該bitmap的使用次數進行+1操作usingCounts = Collections.synchronizedMap(new HashMap ());
@Override
public Bitmap get(String key) {
Bitmap value = super.get(key);
// Increment usage count for value if value is contained in hardCahe
if (value != null) {
Integer usageCount = usingCounts.get(value);
if (usageCount != null) {
//使用次數+1
usingCounts.put(value, usageCount + 1);
}
}
return value;
}@Override
protected int getSize(Bitmap value) {
return value.getRowBytes() * value.getHeight();
}
@Override
protected Bitmap removeNext() {
Integer minUsageCount = null;
Bitmap leastUsedValue = null;
Set> entries = usingCounts.entrySet();
synchronized (usingCounts) {
for (Entry entry : entries) {
if (leastUsedValue == null) {
leastUsedValue = entry.getKey();
minUsageCount = entry.getValue();
} else {
Integer lastValueUsage = entry.getValue();
if (lastValueUsage < minUsageCount) {
minUsageCount = lastValueUsage;
leastUsedValue = entry.getKey();
}
}
}
}
usingCounts.remove(leastUsedValue);
return leastUsedValue;
}
@Override
protected Reference createReference(Bitmap value) {
return new WeakReference(value);
} @Override
public boolean put(String key, Bitmap value) {
if (super.put(key, value)) {
usingCounts.put(value, 0);
return true;
} else {
return false;
}
}
LimitedAgeMemoryCache:
對超出時間限制的緩存對象進行刪除,該類的實現畢竟簡單,具體代碼如下:public class LimitedAgeMemoryCache implements MemoryCache {
private final MemoryCache cache;
private final long maxAge;
private final Map loadingDates = Collections.synchronizedMap(new HashMap());
/**
* @param cache Wrapped memory cache
* @param maxAge Max object age (in seconds). If object age will exceed this value then it'll be removed from
* cache on next treatment (and therefore be reloaded).
*/
public LimitedAgeMemoryCache(MemoryCache cache, long maxAge) {
this.cache = cache;
this.maxAge = maxAge * 1000; // to milliseconds
}
@Override
public boolean put(String key, Bitmap value) {
boolean putSuccesfully = cache.put(key, value);
if (putSuccesfully) {
loadingDates.put(key, System.currentTimeMillis());
}
return putSuccesfully;
}
@Override
public Bitmap get(String key) {
Long loadingDate = loadingDates.get(key);
//判斷是否超時
if (loadingDate != null && System.currentTimeMillis() - loadingDate > maxAge) {
cache.remove(key);
loadingDates.remove(key);
}
return cache.get(key);
}
@Override
public void remove(String key) {
cache.remove(key);
loadingDates.remove(key);
}
@Override
public Collection keys() {
return cache.keys();
}
@Override
public void clear() {
cache.clear();
loadingDates.clear();
}
}
FuzzyKeyMemoryCache:
該緩存的作用就是如果緩存中的有一個key和要加入的keytemp相等,就從緩存中刪除該key指向的bitmap對象,然後把新的key對象加入到緩存中去。具體的邏輯如下:
@Override
public boolean put(String key, Bitmap value) {
// Search equal key and remove this entry
synchronized (cache) {
String keyToRemove = null;
for (String cacheKey : cache.keys()) {
//判斷緩存中對應的key是否存在,存在就刪除
if (keyComparator.compare(key, cacheKey) == 0) {
keyToRemove = cacheKey;
break;
}
}
if (keyToRemove != null) {
cache.remove(keyToRemove);
}
}
return cache.put(key, value);
}@Override
public final boolean put(String key, Bitmap value) {
synchronized (this) {
size += sizeOf(key, value);
Bitmap previous = map.put(key, value);
if (previous != null) {
size -= sizeOf(key, previous);
}
}
//緩存瘦身,把最近最久未使用的bitMap刪除
trimToSize(maxSize);
return true;
}
private void trimToSize(int maxSize) {
while (true) {
String key;
Bitmap value;
synchronized (this) {
Map.Entry toEvict = map.entrySet().iterator().next();
if (toEvict == null) {
break;
}
key = toEvict.getKey();
value = toEvict.getValue();
map.remove(key);
size -= sizeOf(key, value);
}
}
}
IM推送Android客戶端SDK之智能心跳
1. 為什麼TCP連接需要心跳? 因為運營商有一個NAT超時:因為IP v4的IP量有限,運營商分配給手機終端的IP是運營商內網的IP,手機要連接Internet,就需要
Adapter類控件使用之ViewPager(視圖滑動切換工具)的基本使用
(一)概述Android 3.0後引入的一個UI控件——ViewPager(視圖滑動切換工具),實在想不到 如何來稱呼這個控件,他的大概功能:通過
分答是什麼?分答怎麼玩?
果殼網旗下在行在微信公眾號上線了一款付費語音問答新產品——分答。 用戶在分答上可以自我介紹或描述擅長的領域,設置付費問答
Android實現桌面懸浮窗、蒙板效果實例代碼
現在很多安全類的軟件,比如360手機助手,百度手機助手等等,都有一個懸浮窗,可以飄浮在桌面上,方便用戶使用一些常用的操作。今天這篇文章,就是介紹如何實現桌面懸浮窗效果的。