Java内存泄漏介绍

内存管理是Java最重要的优势之一,你只需创建对象,Java垃圾收集器会自动负责分配和释放内存。但是,情况并不那么简单,因为在Java应用程序中经常发生内存泄漏。

本章会说明什么是内存泄漏,为什么发生,以及如何防止它们。

什么是内存泄漏?

内存泄漏的定义:应用程序不再使用的对象,垃圾收集器却无法删除它们,因为它们正在被引用。

为了理解这个定义,我们需要了解对象在内存中的状态。下图说明了什么是未引用的,什么是引用的对象。

从图中可以看出,有被引用的对象和未被引用的对象。未引用的对象将被垃圾收集,而被引用的对象将不会被垃圾收集。未引用的对象肯定是未使用的,因为没有其他对象引用它。但是,未使用的对象并不是全部未被引用,其中一些被引用!这是内存泄漏的来源。

为什么内存泄漏发生?

让我们来看看下面的例子,看看为什么发生内存泄漏。在下面的例子中,对象A是指对象B。A的生命周期(t1 - t4)比B的(t2 - t3)长得多,当应用中不再使用B时,A仍然有一个B的引用,这样垃圾收集器就不能从内存中删除B。这就可能会导致内存不足的问题,因为如果A同时为更多的对象做同样的事情,那么会有很多像B这样的对象没有收集并占用内存空间。

B也可能拥有一堆其他对象的引用,B引用的对象也不会被收集。所有这些未使用的对象将消耗宝贵的内存空间。

如何防止内存泄漏?

以下是防止内存泄漏的一些快速实用技巧。

  • 注意集合类,如HashMap、ArrayList等,因为它们是发现内存泄漏的常见地方。当它们被声明为静态时,它们的生命时间与应用程序的生命时间是相同的。
  • 注意事件监听器和回调。如果一个侦听器被注册了,但是当类不再被使用时,可能会发生内存泄漏。
  • 如果一个类管理自己的内存,程序应该对内存泄漏保持警惕。通常情况下,指向其他对象的成员变量需要为null值。

思考

为什么JDK 6中的substring方法会导致内存泄漏?

原文发布于微信公众号 - Java技术栈(javastack)

原文发表时间:2017-12-08

本文参与腾讯云自媒体分享计划,欢迎正在阅读的你也加入,一起分享。

发表于

我来说两句

0 条评论
登录 后参与评论

相关文章

来自专栏醉梦轩

Python和JavaScript中的生成器与协程

Python和JavaScript中都有生成器(Generator)和协程(coroutine)的概念。本文通过分析两者在这两种语言上的使用案例,来对比它们的差...

25920
来自专栏刘君君

MAT内存分析工具使用

33960
来自专栏IT技术精选文摘

易犯的Java内存泄漏代码

Java隐式地通过GC(守护线程)回收内存。 GC定期检查是否存在无法访问的对象,或者确切地说,没有指向该对象的引用。如果是这样,GC回收新可用的内存。 现在...

23170
来自专栏韩伟的专栏

框架设计原则和规范(完)

祝大家圣诞节快乐!有事没事别出门,外面太!挤!了! 此文是《.NET:框架设计原则、规范》的读书笔记,本文内容较多,共分九章,今天推送最后一章。 1. 什么是好...

29640
来自专栏向治洪

类加载器原理

1.类的加载过程   JVM将类加载过程分为三个步骤:装载(Load),链接(Link)和初始化(Initialize)链接又分为三个步骤,如下图所示: ?...

21980
来自专栏WindCoder

JVM-Java内存区域

JVM在执行Java程序的过程中会把它所管理的内存划分为若干个不同的数据区域,都有着各自的用途以及创建和销毁时间。包括以下几个如图所示的运行时数据区域:

26010
来自专栏WindCoder

JVM基础小结

在内存区,方法区和堆是所有Java线程共享的,而Java虚拟机栈、本地方法栈、PC寄存器则由每个线程私有。

20120
来自专栏葡萄城控件技术团队

JavaScript中的内存泄漏以及如何处理

14820
来自专栏温安适的blog

手写jvm中的各种OOM

41490
来自专栏栗霖积跬步之旅

深入理解java虚拟机-第二章:java内存区域与内存泄露异常

java将内存的管理(主要是回收工作),交由jvm管理,确实很省事,但是一点jvm因内存出现问题,排查起来将会很困难,为了能够成为独当一面的大牛呢,自然要了解...

11620

扫码关注云+社区

领取腾讯云代金券