プログラマってこんなかんじ??

アプリ作ったり歌ったりしてます

LruCache 使ってみた(android.util.LruCache)

GoogleI/O 2012 のセッションで LruCache の話が出てたので使ってみた。


Doing More With Less: Being a Good Android Citizen
pdf(右側の 「Session presentation」 リンク) の p.8 くらいから。


LruCache(android.util.LruCache)

  1. Least Recently Used アルゴリズム(wiki) を用いたキャッシュ管理クラス
  2. 中身は LinkedHashMap
  3. インスタンス生成時に保持キャッシュサイズの最大値を指定
  4. 要素がputされたときに↑を超えていたら既存要素を自動的に破棄
  5. API Level 12
  6. support library(v4) にもあるから APILevel が ↑以下でも使える


使い方は基本的にこんなかんじ。


実装方法

  1. LruCache の拡張クラスを作成
  2. コンストラクタ保持キャッシュサイズ最大値 を定義(↓のsizeOfの合計値上限)
  3. LruCache#sizeOf を override して 各要素のサイズ計算方法 を定義
  4. LruCache#entryRemoved を override して 各要素の破棄処理 を定義


サンプルコード。

private void testLruCache() {
    // cache要素最大数 10個
    LruCache lruCache = new BitmapLruCache(10);

    // cache要素追加
    String key = ~;
    Bitmap val = ~;
    lruCache.put(key, val);

    // cache要素取得
    Bitmap cache = lruCache.get(key);

    // cache解放処理(全要素)
    lruCache.evictAll();
}

private static class BitmapLruCache extends LruCache<String, Bitmap> {

    public BitmapLruCache(int maxSize) {
        super(maxSize);
    }

    @Override
    protected int sizeOf(String key, Bitmap value) {
        // default では 1 を返却
        return super.sizeOf(key, value);
    }

    @Override
    protected void entryRemoved(boolean evicted, String key, 
        Bitmap oldValue, Bitmap newValue) {

        // cache解放処理
        if (!oldValue.isRecycled()) {
            oldValue.recycle();
            oldValue = null;
        }
    }
}


この実装の場合、こんな感じになる。

  • 保持キャッシュ(Bitmap)最大数は 10個
  • 保持キャッシュ数が 10個 を超えると要素が解放されていく(Bitmap#recycle)