LruCache不工作

时间:2013-03-17 10:39:40

标签: android android-lru-cache

    final int maxMemory = (int) (Runtime.getRuntime().maxMemory() / 1024);
    final int cacheSize = maxMemory / 8;
    mMemoryCache = new LruCache<String, Bitmap>(cacheSize) {
            @Override
            protected int sizeOf(String key, Bitmap bitmap) {
                // The cache size will be measured in kilobytes rather than
                // number of items.
                return bitmap.getByteCount() / 1024;
            }
        };
    URL url = new URL("http://s2.goodfon.ru/image/260463-1920x1200.jpg");
    Bitmap bitmap = BitmapFactory.decodeStream((InputStream) url.getContent(), null, options);
    if(bitmap != null)
        Log.i("Success", "BITMAP IS NOT NULL");

    String key = "myKey";
    Log.i("Get is null", "putting myKey");
    mMemoryCache.put(key, bitmap);

    Bitmap newBitmap = mMemoryCache.get(key);
    if(newBitmap == null)
        Log.i("newBitmap", "is null");

你好,这是一个代码。我成功从URL获取位图(Log说Bitmap不是null,我可以很容易地显示它)。然后我试图将它放入LruCache并将其恢复,但它返回null。 (Log表示newBitmap为null)。我的错误在哪里?请告诉我。 Android 4.1.2缓存大小8192 Kb。

3 个答案:

答案 0 :(得分:8)

如果它在磁盘上是1.19 MB但在内存中是〜9 MB,这意味着作为压缩的JPEG文件,它是1.19 MB,一旦你将其提取到可以显示的Bitmap(未压缩)中,它将占用9 MB在记忆中。如果它是代码片段中url建议的1920 x 1200像素图像,则图像将占用1920 x 1200 x 4字节的内存(每个像素4个字节,表示ARGB值从0到256倍230万总像素= 9,216,000字节)。如果您使用1/8的可用内存用于此缓存,则可能/可能9MB超过总内存空间,因此Bitmap永远不会进入缓存或立即被驱逐。

你可能会想要在解码时对图像进行下采样,如果它那么大(使用BitmapFactory.Options.inSampleSize ...很多文档在网上使用,如果你还不熟悉的话。)< / p>

此外,您正在使用Runtime.maxMemory来计算缓存大小。这意味着您正在请求允许整个VM使用的最大内存量。

http://developer.android.com/reference/java/lang/Runtime.html#maxMemory%28%29

更常见的方法是使用ActivityManager.getMemoryClass()方法返回给您的值。

以下是文档中的示例代码段和方法定义,供参考。

    ActivityManager am = (ActivityManager) getSystemService(Context.ACTIVITY_SERVICE);
    int memClassBytes = am.getMemoryClass() * 1024 * 1024;
    int cacheSize = memClassBytes / 8;
    mMemoryCache = new LruCache<String, Bitmap>(cacheSize)

http://developer.android.com/reference/android/app/ActivityManager.html#getMemoryClass%28%29

答案 1 :(得分:0)

您还可以回收从lrucache

弹出的位图
final Bitmap bmp = mLruCache.put(key, data);
if (bmp != null)
    bmp.recycle();

答案 2 :(得分:0)

在以下行中将Runtime maxMemory除以1024时,Android示例出错了:

final int maxMemory = (int) (Runtime.getRuntime().maxMemory() / 1024);

maxMemory的单位是Byte,它与'cacheSize'相同('/ 8'只表示它将使用当前Activity的八分之一可用内存)。因此,'/ 1024'会使'cacheSize'非常小,这样就不会在'mMemoryCache'中实际“缓存”位图。

解决方案将在上面的代码中删除'/ 1024'。