在我的应用中,我正在使用颜色代码创建一个位图,如下所示:
int width=getImageWidth();
int height=getImageHeight();
int[] array=getbitmap();
int[] colorsAsIntegers = new int[width*height];
int i = 0;
int j = 0;
while (i<width*height*4) {
colorsAsIntegers[j] = Color.argb(array[i], array[i+1], array[i+2],
array[i+3]);
i += 4;
j++;
}
myBitmap=Bitmap.createBitmap(colorsAsIntegers,
width,
height,
Bitmap.Config.ARGB_8888);
经常我得到outofmemoryerror :( 那么我如何使用BitmapFactory优化来避免这个问题呢? 因为我没有输入流或文件,所以我只有一个数组 包含我的像素
谢谢
答案 0 :(得分:3)
一些事情......
Android确实存在严重的位图问题。它们被分配在非垃圾收集的内存中。哪个好。收集拥有的Bitmap时,它们会被垃圾收集。他们不做的是在压缩堆时重新定位。这可能会导致堆碎片导致的过早的内存不足错误。解决方案:一旦完成位图,就调用Bitmap.recycle。这释放了非gc内存,并减少了碎片问题。
您还可以通过创建空位图,然后从单个小缓冲区逐行复制像素来降低内存压力。 Java gc也不特别喜欢大型数组(尽管可以在gc期间重新定位大型数组)。与过早的垃圾收集相比,性能损失很小,并且可以忽略不计。这样做会减少49.99%的内存使用量。
答案 1 :(得分:1)
尝试按照here
显示对图像进行下采样答案 2 :(得分:1)
请先解码文件,为此使用此代码:
public static Bitmap new_decode(File f) {
// decode image size
BitmapFactory.Options o = new BitmapFactory.Options();
o.inJustDecodeBounds = true;
o.inDither = false; // Disable Dithering mode
o.inPurgeable = true; // Tell to gc that whether it needs free memory,
// the Bitmap can be cleared
o.inInputShareable = true; // Which kind of reference will be used to
// recover the Bitmap data after being
// clear, when it will be used in the future
try {
BitmapFactory.decodeStream(new FileInputStream(f), null, o);
} catch (FileNotFoundException e1) {
// TODO Auto-generated catch block
e1.printStackTrace();
}
// Find the correct scale value. It should be the power of 2.
final int REQUIRED_SIZE = 300;
int width_tmp = o.outWidth, height_tmp = o.outHeight;
int scale = 1;
while (true) {
if (width_tmp / 1.5 < REQUIRED_SIZE && height_tmp / 1.5 < REQUIRED_SIZE)
break;
width_tmp /= 1.5;
height_tmp /= 1.5;
scale *= 1.5;
}
// decode with inSampleSize
BitmapFactory.Options o2 = new BitmapFactory.Options();
// o2.inSampleSize=scale;
o.inDither = false; // Disable Dithering mode
o.inPurgeable = true; // Tell to gc that whether it needs free memory,
// the Bitmap can be cleared
o.inInputShareable = true; // Which kind of reference will be used to
// recover the Bitmap data after being
// clear, when it will be used in the future
// return BitmapFactory.decodeStream(new FileInputStream(f), null, o2);
try {
// return BitmapFactory.decodeStream(new FileInputStream(f), null,
// null);
Bitmap bitmap= BitmapFactory.decodeStream(new FileInputStream(f), null, null);
System.out.println(" IW " + width_tmp);
System.out.println("IHH " + height_tmp);
int iW = width_tmp;
int iH = height_tmp;
return Bitmap.createScaledBitmap(bitmap, iW, iH, true);
} catch (OutOfMemoryError e) {
// TODO: handle exception
e.printStackTrace();
// clearCache();
// System.out.println("bitmap creating success");
System.gc();
return null;
// System.runFinalization();
// Runtime.getRuntime().gc();
// System.gc();
// decodeFile(f);
} catch (FileNotFoundException e) {
// TODO Auto-generated catch block
e.printStackTrace();
return null;
}
}
您可以使用android:largeHeap="true"
来请求更大的堆大小
在清单文件中提到这个以使用大堆。