「java中的oom」java中的oom是什么意思

博主:adminadmin 2022-12-24 19:42:07 64

本篇文章给大家谈谈java中的oom,以及java中的oom是什么意思对应的知识点,希望对各位有所帮助,不要忘了收藏本站喔。

本文目录一览:

java oom异常怎么解决方案

在 Java中,JavaVM拥有自动管理内存的功能,Java的GC能够进行垃圾回收,但是Android中如果ImageView使用过多的Bitmap的话,经常会报OOM(内存溢出)。

造成内存溢出及解决方案:

1.使用BitmapFactory.decodeStream替代createBitmap方法

原因是该方法直读取图片字节,调用JNInativeDecodeAsset()来完成decode,无需再使用java层的createBitmap。

2.使用压缩读取技术

BitmapFactory.Options options = new BitmapFactory.Options();

options.inJustDecodeBounds = true;

BitmapFactory.decodeFile(imageSdUri, options);

final int height = options.outHeight;

final int width = options.outWidth;

options.inSampleSize = 1;

int w = 320;

int h = 480;

h = w*height/width;//计算出宽高等比率

int a = options.outWidth/ w;

int b = options.outHeight / h;

options.inSampleSize = Math.max(a, b);

options.inJustDecodeBounds = false;

Bitmap bitmap = BitmapFactory.decodeFile(imageSdUri, options);

3.及时释放Bitamp

Bitmap对象在不使用时,我们应该先调用recycle()释放内存,然后才它设置为null.虽然recycle()从源码上看,调用它应该能立即释放Bitmap的主要内存,但是测试结果显示它并没能立即释放内存。但是我它应该还是能大大的加速Bitmap的主要内存的释放。

oom的解决方法有哪些,请说明

1. 正确释放drawable的方式:

Bitmap bm = BitmapFactory.decodeResource(this.getResources(), R.drawable.splash);

BitmapDrawable bd = new BitmapDrawable(this.getResources(), bm);

mBtn.setBackgroundDrawable(bd);

来代替mBtn.setBackgroundResource(R.drawable.splash)。

销毁的时候使用:

BitmapDrawable bd = (BitmapDrawable)mBtn.getBackground();

mBtn.setBackgroundResource(0);//别忘了把背景设为null,避免onDraw刷新背景时候出现used a recycled bitmap错误

bd.setCallback(null);

bd.getBitmap().recycle();

2. 使用字节流,突破Android heap size的限制

从中不难发现,bitmap的存放位置根据Android版本的不同真的有所不同。好了,下面就是找出怎么把图片存放到native heap里就行了,BitmapFactory里就那么几个decode方法,很容易找到BitmapFactory .decodeStream就可以解决。下面贴一下代码:

BitmapFactory.Options options = new BitmapFactory.Options();

options.inPreferredConfig = Config.ARGB_8888;

options.inPurgeable = true;// 允许可清除

options.inInputShareable = true;// 以上options的两个属性必须联合使用才会有效果

String sname = String.format( “xxx.png”, sTowerStyle, j, sDirction, i);

InputStream is = am.open(sname);

arrBmp[ iBmpIndex] = BitmapFactory .decodeStream(is, null, options);

ok搞定收工。

尽量不要使用setImageBitmap或setImageResource或BitmapFactory.decodeResource来设置一张大图,

因为这些函数在完成decode后,最终都是通过java层的createBitmap来完成的,需要消耗更多内存。

因此,改用先通过BitmapFactory.decodeStream方法,创建出一个bitmap,再将其设为ImageView的 source,

decodeStream最大的秘密在于其直接调用JNInativeDecodeAsset()来完成decode,

无需再使用java层的createBitmap,从而节省了java层的空间。

如果在读取时加上图片的Config参数,可以跟有效减少加载的内存,从而跟有效阻止抛out of Memory异常

另外,decodeStream直接拿的图片来读取字节码了, 不会根据机器的各种分辨率来自动适应,

使用了decodeStream之后,需要在hdpi和mdpi,ldpi中配置相应的图片资源,

否则在不同分辨率机器上都是同样大小(像素点数量),显示出来的大小就不对了。

关于JAVA文件上传的奇怪OOM问题

可能是jvm运行时内存不足吧,你试下

java -Xms512m -Xmx512m -XX:MaxPermSize=128m -cp lib/bootstart.jar; TestJava

Xmx 用来设置你的应用程序能够使用的最大内存数(看好,致使你的应用程序,不是整个jvm),如果你的程序要花很大内存的话,那就需要修改缺省的设置,比如配置tomcat的时候,如果流量啊程序啊都很大的话就需要加大这个值了,不过有一点是要记住的,不要大得超过你的机器的内存,那样你的机器会受不了的,到时候就死翘翘了。

Xms 用它来设置程序初始化的时候内存栈的大小,增加这个值的话你的程序的启动性能会得到提高。不过同样有前面的限制,以及受到xmx的限制。

java oom 进程为什么退出

防止重要的系统进程触发(OOM)机制而被杀死:可以设置参数/proc/PID/oom_adj为-17,可临时关闭linux内核的OOM机制。内核会通过特定的算法给每个进程计算一个分数来决定杀哪个进程,每个进程的oom分数可以/proc/PID/oom_score中找到。我们运维过程中保护的一般是sshd和一些管理agent。

保护某个进程不被内核杀掉可以这样操作:

# echo -17 /proc/$PID/oom_adj

如何防止sshd被杀,可以这样操作:

# pgrep -f "/usr/sbin/sshd" | while read PID;do echo -17 /proc/$PID/oom_adj;done

可以在计划任务里加入这样一条定时任务,就更安全了:

#/etc/cron.d/oom_disable

*/1**** root pgrep -f "/usr/sbin/sshd" | while read PID;do echo -17 /proc/$PID/oom_adj;done

为了避免重启失效,可以写入/etc/rc.d/rc.local

echo -17 /proc/$(pidof sshd)/oom_adj

至于为什么用-17而不用其他数值(默认值为0),这个是由linux内核定义的,查看内核源码可知:

以linux-3.3.6版本的kernel源码为例,路径为linux-3.6.6/include/linux/oom.h,阅读内核源码可知oom_adj的可调值为15到-16,其中15最大-16最小,-17为禁止使用OOM。oom_score为2的n次方计算出来的,其中n就是进程的oom_adj值,所以oom_score的分数越高就越会被内核优先杀掉。

当然还可以通过修改内核参数禁止OOM机制

# sysctl -w vm.panic_on_oom=1

vm.panic_on_oom = 1 //1表示关闭,默认为0表示开启OOM

# sysctl -p

java中的oom的介绍就聊到这里吧,感谢你花时间阅读本站内容,更多关于java中的oom是什么意思、java中的oom的信息别忘了在本站进行查找喔。

The End

发布于:2022-12-24,除非注明,否则均为首码项目网原创文章,转载请注明出处。