Java.lang.OutOfMemoryError: bitmap size exceeds VM budget。

7
我有一个懒加载图片的ListView。我还使用这个教程来更好地管理内存,并在我的ArrayList中存储了SoftReference位图图像。
我的ListView从数据库中加载8张图片,一旦用户滚动到底部,它就会加载另外8张图片。当图片数量超过35张时,我的应用程序会因为OutOfMemoryError而强制关闭。
我无法理解的是,我已经在try catch语句中写了代码:
try
{
    BitmapFactory.Options o = new BitmapFactory.Options();
    o.inJustDecodeBounds = true;
    BitmapFactory.decodeByteArray(image, 0, image.length, o);

    //Find the correct scale value. It should be the power of 2.
    int width_tmp = o.outWidth, height_tmp = o.outHeight;
    int scale = 1;

    while(true)
    {
        if(width_tmp/2 < imageWidth || height_tmp/2 < imageHeight)
        {
            break;
        }

        width_tmp/=2;
        height_tmp/=2;
        scale++;
    }

    //Decode with inSampleSize
    BitmapFactory.Options o2 = new BitmapFactory.Options();
    o2.inSampleSize = scale;
    bitmapImage = BitmapFactory.decodeByteArray(image, 0, image.length, o2);        
}
catch (Exception e)
{
    e.printStackTrace();
}

但是try catch块没有捕获OutOfMemory异常,据我所知,当应用程序内存不足时,SoftReference位图图像应该被清除,以防止抛出OutOfMemory异常。

我在这里做错了什么?

3个回答

9
我想这篇文章可能会对你有所帮助。
//decodes image and scales it to reduce memory consumption
private Bitmap decodeFile(File f){
    try {
        //Decode image size
        BitmapFactory.Options o = new BitmapFactory.Options();
        o.inJustDecodeBounds = true;
        BitmapFactory.decodeStream(new FileInputStream(f),null,o);

        //The new size we want to scale to
        final int REQUIRED_SIZE=70;

        //Find the correct scale value. It should be the power of 2.
        int width_tmp=o.outWidth, height_tmp=o.outHeight;
        int scale=1;
        while(true){
            if(width_tmp/2<REQUIRED_SIZE || height_tmp/2<REQUIRED_SIZE)
                break;
            width_tmp/=2;
            height_tmp/=2;
            scale*=2;
        }

        //Decode with inSampleSize
        BitmapFactory.Options o2 = new BitmapFactory.Options();
        o2.inSampleSize=scale;
        return BitmapFactory.decodeStream(new FileInputStream(f), null, o2);
    } catch (FileNotFoundException e) {}
    return null;
}

应该选择这个解决方案! - Pascal

4

啊,我的错...完全不知道。有什么我可以做来防止它发生吗?我完全被卡住了。 - mlevit
如果有解决问题的方法,或者想通过例如在单独的进程中启动新活动来告知用户,那么捕获OutOfMemoryError是完全有道理的。 - arberg

0

错误和异常是从Throwable继承的子类。 错误应该如此严重,以至于不应该捕获它们。

但你可以捕获任何东西。

try
{ 
}
catch (Throwable throwable)
{
}

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接