千家信息网

Java中内存泄漏是什么意思

发表于:2024-10-10 作者:千家信息网编辑
千家信息网最后更新 2024年10月10日,小编给大家分享一下Java中内存泄漏是什么意思,相信大部分人都还不怎么了解,因此分享这篇文章给大家参考一下,希望大家阅读完这篇文章后大有收获,下面让我们一起去了解一下吧!一、什么是内存泄漏内存泄漏是指
千家信息网最后更新 2024年10月10日Java中内存泄漏是什么意思

小编给大家分享一下Java中内存泄漏是什么意思,相信大部分人都还不怎么了解,因此分享这篇文章给大家参考一下,希望大家阅读完这篇文章后大有收获,下面让我们一起去了解一下吧!

一、什么是内存泄漏

内存泄漏是指你向系统申请分配内存进行使用(new/malloc),然后系统在堆内存中给这个对象申请一块内存空间,但当我们使用完了却没有归系统(delete),导致这个不使用的对象一直占据内存单元,造成系统将不能再把它分配给需要的程序。

一次内存泄漏的危害可以忽略不计,但是内存泄漏堆积则后果很严重,无论多少内存,迟早会被占完,造成内存泄漏。

二、Java内存泄漏引起的原因

1、静态集合类引起内存泄漏:

像HashMap、Vector等的使用最容易出现内存泄露,这些静态变量的生命周期和应用程序一致,他们所引用的所有的对象Object也不能被释放,因为他们也将一直被Vector等引用着。

Static Vector v = new Vector(10);for (int i = 1; i<100; i++){Object o = new Object();v.add(o);o = null ;}

在这个例子中,循环申请Object 对象,并将所申请的对象放入一个Vector 中,如果仅仅释放引用本身(o=null),那么Vector 仍然引用该对象,所以这个对象对GC 来说是不可回收的。因此,如果对象加入到Vector 后,还必须从Vector 中删除,最简单的方法就是将Vector对象设置为null。

2、当集合里面的对象属性被修改后,再调用remove()方法时不起作用。

public static void main(String[] args){Set set = new HashSet();Person p1 = new Person( "唐僧" , "pwd1" , 25 );Person p2 = new Person( "孙悟空" , "pwd2" , 26 );Person p3 = new Person( "猪八戒" , "pwd3" , 27 );set.add(p1);set.add(p2);set.add(p3);System.out.println( "总共有:" +set.size()+ " 个元素!" ); //结果:总共有:3 个元素!p3.setAge( 2 ); //修改p3的年龄,此时p3元素对应的hashcode值发生改变set.remove(p3); //此时remove不掉,造成内存泄漏set.add(p3); //重新添加,居然添加成功System.out.println( "总共有:" +set.size()+ " 个元素!" ); //结果:总共有:4 个元素!for (Person person : set){System.out.println(person);}}

3、监听器

在java编程中,我们都需要和监听器打交道,通常一个应用当中会用到很多监听器,我们会调用一个控件的诸如addXXXListener()等方法来增加监听器,但往往在释放对象的时候却没有记住去删除这些监听器,从而增加了内存泄漏的机会。

4、各种连接

比如数据库连接(dataSourse.getConnection()),网络连接(socket)和io连接,除非其显式的调用了其close()方法将其连接关闭,否则是不会自动被GC 回收的。对于Resultset 和Statement 对象可以不进行显式回收,但Connection 一定要显式回收,因为Connection 在任何时候都无法自动回收,而Connection一旦回收,Resultset 和Statement 对象就会立即为NULL。但是如果使用连接池,情况就不一样了,除了要显式地关闭连接,还必须显式地关闭Resultset Statement 对象(关闭其中一个,另外一个也会关闭),否则就会造成大量的Statement 对象无法释放,从而引起内存泄漏。这种情况下一般都会在try里面去的连接,在finally里面释放连接。

5、内部类和外部模块的引用

内部类的引用是比较容易遗忘的一种,而且一旦没释放可能导致一系列的后继类对象没有释放。此外程序员还要小心外部模块不经意的引用,例如程序员A 负责A 模块,调用了B 模块的一个方法如:

public void registerMsg(Object b);

这种调用就要非常小心了,传入了一个对象,很可能模块B就保持了对该对象的引用,这时候就需要注意模块B 是否提供相应的操作去除引用。

6、单例模式

不正确使用单例模式是引起内存泄漏的一个常见问题,单例对象在初始化后将在JVM的整个生命周期中存在(以静态变量的方式),如果单例对象持有外部的引用,那么这个对象将不能被JVM正常回收,导致内存泄漏,考虑下面的例子:

class A{public A(){B.getInstance().setA( this );}....}//B类采用单例模式class B{private A a;private static B instance= new B();public B(){}public static B getInstance(){return instance;}public void setA(A a){this .a=a;}//getter...}

显然B采用singleton模式,它持有一个A对象的引用,而这个A类的对象将不能被回收。想象下如果A是个比较复杂的对象或者集合类型会发生什么情况。

7、redis缓存雪崩、缓存穿透、缓存击穿

三、内存泄漏的危害

1、频繁GC

系统分配给每个应用的内存资源都是有限的,内存泄漏导致其他组件可用的内存变少后,一方面会使得GC的频率加剧,再发生GC的时候,所有进程都必须等待,GC的频率越高,用户越容易感应到卡顿。另一方面内存变少,可能使得系统额外分配给该对象一些内存,而影响整个系统的运行情况

2、导致程序运行崩溃

一旦内存不足以为某些对象分配所需要的空间,将会导致程序崩溃,造成体验差。

以上是"Java中内存泄漏是什么意思"这篇文章的所有内容,感谢各位的阅读!相信大家都有了一定的了解,希望分享的内容对大家有所帮助,如果还想学习更多知识,欢迎关注行业资讯频道!

内存 对象 模块 程序 系统 元素 方法 监听器 监听 情况 模式 分配 时候 篇文章 缓存 静态 应用 意思 例子 内容 数据库的安全要保护哪些东西 数据库安全各自的含义是什么 生产安全数据库录入 数据库的安全性及管理 数据库安全策略包含哪些 海淀数据库安全审计系统 建立农村房屋安全信息数据库 易用的数据库客户端支持安全管理 连接数据库失败ssl安全错误 数据库的锁怎样保障安全 大连网络技术培训 石家庄互联网公司软件开发 socket代理服务器软件 超市购物系统设计数据库源代码 青浦区信息化软件开发批发价格 网络安全学习会议记录 魔兽怀旧是那个服务器 车载网络技术怎么样 网络安全方面职业认证 有 首都网络安全日参与部门 网络安全手招报 电脑端口进入服务器代码 苏州安卓软件开发哪家便宜 千晴网络技术有限公司 网络安全的十大案例 制作软件开发公司 确认该数据库是否删除的代码 工业网络安全实训室 云服务器租赁的安全措施 售后服务规范监控服务器 嵌入式软件开发工程师上海 守护网络安全简报 网络安全宣传周用什么看 网络安全预防工作包括演练 孝义软件开发有限公司 湖北电商网络安全维护管理系统 软件开发首选桌面指纹仪哪家便宜 c 窗体连数据库步骤 魔兽世界轮回服各服务器人数 网络技术学习用品礼物
0