1/*
2 * Copyright (C) 2008 Esmertec AG.
3 * Copyright (C) 2008 The Android Open Source Project
4 *
5 * Licensed under the Apache License, Version 2.0 (the "License");
6 * you may not use this file except in compliance with the License.
7 * You may obtain a copy of the License at
8 *
9 *      http://www.apache.org/licenses/LICENSE-2.0
10 *
11 * Unless required by applicable law or agreed to in writing, software
12 * distributed under the License is distributed on an "AS IS" BASIS,
13 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
14 * See the License for the specific language governing permissions and
15 * limitations under the License.
16 */
17
18package com.google.android.mms.util;
19
20import android.util.Log;
21
22import java.util.HashMap;
23
24public abstract class AbstractCache<K, V> {
25    private static final String TAG = "AbstractCache";
26    private static final boolean DEBUG = false;
27    private static final boolean LOCAL_LOGV = false;
28
29    private static final int MAX_CACHED_ITEMS  = 500;
30
31    private final HashMap<K, CacheEntry<V>> mCacheMap;
32
33    protected AbstractCache() {
34        mCacheMap = new HashMap<K, CacheEntry<V>>();
35    }
36
37    public boolean put(K key, V value) {
38        if (LOCAL_LOGV) {
39            Log.v(TAG, "Trying to put " + key + " into cache.");
40        }
41
42        if (mCacheMap.size() >= MAX_CACHED_ITEMS) {
43            // TODO Should remove the oldest or least hit cached entry
44            // and then cache the new one.
45            if (LOCAL_LOGV) {
46                Log.v(TAG, "Failed! size limitation reached.");
47            }
48            return false;
49        }
50
51        if (key != null) {
52            CacheEntry<V> cacheEntry = new CacheEntry<V>();
53            cacheEntry.value = value;
54            mCacheMap.put(key, cacheEntry);
55
56            if (LOCAL_LOGV) {
57                Log.v(TAG, key + " cached, " + mCacheMap.size() + " items total.");
58            }
59            return true;
60        }
61        return false;
62    }
63
64    public V get(K key) {
65        if (LOCAL_LOGV) {
66            Log.v(TAG, "Trying to get " + key + " from cache.");
67        }
68
69        if (key != null) {
70            CacheEntry<V> cacheEntry = mCacheMap.get(key);
71            if (cacheEntry != null) {
72                cacheEntry.hit++;
73                if (LOCAL_LOGV) {
74                    Log.v(TAG, key + " hit " + cacheEntry.hit + " times.");
75                }
76                return cacheEntry.value;
77            }
78        }
79        return null;
80    }
81
82    public V purge(K key) {
83        if (LOCAL_LOGV) {
84            Log.v(TAG, "Trying to purge " + key);
85        }
86
87        CacheEntry<V> v = mCacheMap.remove(key);
88
89        if (LOCAL_LOGV) {
90            Log.v(TAG, mCacheMap.size() + " items cached.");
91        }
92
93        return v != null ? v.value : null;
94    }
95
96    public void purgeAll() {
97        if (LOCAL_LOGV) {
98            Log.v(TAG, "Purging cache, " + mCacheMap.size()
99                    + " items dropped.");
100        }
101        mCacheMap.clear();
102    }
103
104    public int size() {
105        return mCacheMap.size();
106    }
107
108    private static class CacheEntry<V> {
109        int hit;
110        V value;
111    }
112}
113