一.Java的垃圾回收机制

Java的垃圾回收机制(java garbage collection)是Java虚拟机提供的能力,用于在空闲时间以不定时的方式动态回收无任何引用的对象占据的堆内存空间。

注意粗体字的地方,java的垃圾回收线程是优先级比较低的线程,什么时候进行垃圾回收难以确定。当某些对象被标记为垃圾对象后,等垃圾回收线程运行时,就会将这些对象回收(确切的说应该是回收这些对象所占的堆内存空间)。

二.什么样的对象会被标记成垃圾对象呢?

  1. 一般来说,所有指向对象的引用都已失效,不可能再有程序能调用到这个对象,那么这个对象就成了垃圾,应该被回收。
  2. 根据这个思路,很容易就能想到用《引用计数》的办法来确定一个对象是否是垃圾。即每当多一个引用指向对象时,引用计数加一,每当少一个引用指向对象时,引用计数减一,引用计数减到零,对象就可以被回收了。
  3. 然而引用计数有一个致命问题不好解决,就是循环引用的问题。比如说一个循环链表,他们循环引用者,引用计数永远不会为零,但是实际上程序已经不能访问他们了,他们应该被回收。(如果还没明白循环引用,第五步之后有代码说明)
  4. 所以Java实际上是使用基于GC Roots的可达性分析,什么是GC Roots?所有类的静态变量,每个线程调用栈上的本地变量(实际上我们编程时也是要从这些地方开始访问数据),所有这些对象,以及被这些对象所指向的对象,都是活的对象。活的对象所指向的对象也是活的对象。GC通过有向图的进行可达性分析,不可达的对象就被视为是垃圾对象。
  5. 所以只要在GC的时刻,让程序暂停运行,然后从GC Roots开始分析,最后没有被标记为活对象的对象就是垃圾了。

*代码事例解释什么是循环引用:

   

  如上图所示,假设我们有两个类分别是A和B,A类中有一个字段是B类的类型,B类中有一个字段是A类类型,现在分别new一个A类对象和new一个B类对象,此时引用a指向刚new出来的A类对象,引用b指向刚new出来的B类对象,然后将两个类中的字段互相引用一下,这样即使下面进行a = null和b = null,但是A类对象仍然被B类对象中的字段引用着,尽管现在A类和B类独享都已经访问不到了,但是引用计数却都不为0.

三.Java中有哪几种引用

  • 强引用(StrongReference):强引用就是我们平时使用的引用,是使用最普遍的引用。如果一个对象具有强引用,那垃圾回收器绝不会回收它(结合上面,一个对象有强引用,那么这个对象一定可达,也就是说明这个对象是活的)。当内存空间不足,Java虚拟机宁愿抛出OutOfMemoryError错误,使程序异常终止,也不会靠随意回收具有强引用的对象来解决内存不足的问题。(简记:永不回收)
  • 软引用(SoftReference):如果一个对象只具有软引用,则内存空间足够,垃圾回收器就不会回收它;如果内存空间不足了,就会回收这些对象的内存。只要垃圾回收器没有回收它,该对象就可以被程序使用。所以,软引用可用来实现内存敏感的高速缓存。(简记:内存不足再回收)
  • 弱引用(WeakReference):弱引用与软引用的区别在于:弱引用的对象拥有更短暂的生命周期。在垃圾回收器线程扫描它所管辖的内存区域的过程中,一旦发现了只具有弱引用的对象,不管当前内存空间足够与否,都会回收它的内存。不过,由于垃圾回收器是一个优先级很低的线程,因此不一定会很快发现那些只具有弱引用的对象。(简记:遇到就回收)
  • 虚引用(PhantomReference):“虚引用”顾名思义,就是形同虚设,与其他几种引用都不同,虚引用并不会决定对象的生命周期。如果一个对象仅持有虚引用,那么它就和没有任何引用一样,在任何时候都可能被垃圾回收器回收。虚引用主要用来跟踪对象被垃圾回收器回收的活动。虚引用与软引用和弱引用的一个区别在于:虚引用必须和引用队列(ReferenceQueue)联合使用。当垃圾回收器准备回收一个对象时,如果发现它还有虚引用,就会在回收对象的内存之前,把这个虚引用加入到与之关联的引用队列中。(简记:形同虚设)

值得区分的一点是,软引用和弱引用是可选的时候和引用队列联合使用,如果与引用队列联合使用,那么当所引用的对象被垃圾回收,Java虚拟机就会把这个弱(或软)引用加入到与之关联的引用队列中。而虚引用是必须和引用队列联合使用。

记录Java的垃圾回收机制和几种引用的更多相关文章

  1. java JVM垃圾回收机制

    Java语言出来之前,大家都在拼命的写C或者C++的程序,而此时存在一个很大的矛盾,C++等语言创建对象要不断的去开辟空间,不用的时候有需要不断的去释放控件,既要写构造函数,又要写析构函数,很多时候都 ...

  2. JVM系列(三):java的垃圾回收机制

    java垃圾回收机制介绍    上一篇讲述了JVM的内存模型,了解了到了绝大部分的对象是分配在堆上面的,我们在编码的时候并没有显示的指明哪些对象需要回收,但是程序在运行的过程中是会一直创建对象的,之所 ...

  3. 了解java中垃圾回收机制

    Java的垃圾回收机制是Java环境自带有的,它不像c语言的malloc申请空间后需要Free()函数来释放,而Java中的代码块中所申请的空间可在程序执行完成后自动释放,但是是有局限性的,代码块所占 ...

  4. 面试官,不要再问我“Java GC垃圾回收机制”了

    Java GC垃圾回收几乎是面试必问的JVM问题之一,本篇文章带领大家了解Java GC的底层原理,图文并茂,突破学习及面试瓶颈. 楔子-JVM内存结构补充 在上篇<JVM之内存结构详解> ...

  5. 【Java学习笔记】Java的垃圾回收机制

    搬以前写的博客[2014-12-30 15:07] 以前很少关注内存的问题,基本没有关注,这方面的小白,原因在于自己都是写的自我娱乐的小程序,不关注性能,不是提供服务.而企业级别的应用在程序稳健性方面 ...

  6. JAVA的垃圾回收机制

    1. 垃圾回收的意义 在C++中,对象所占的内存在程序结束运行之前一直被占用,在明确释放之前不能分配给其它对象:而在Java中,当没有对象引用指向原先分配给某个对象的内存时,该内存便成为垃圾.JVM的 ...

  7. 全面分析Java的垃圾回收机制

    Java的堆是一个运行时数据区,类的实例(对象)从中分配空间.Java虚拟机(JVM)的堆中储存着正在运行的应用程序所建立的所有对象,这些对象通过new.newarray.anewarray和mult ...

  8. Java内存垃圾回收机制(转贴)

    Java的堆是一个运行时数据区,类的实例(对象)从中分配空间.Java虚拟机(JVM)的堆中储存着正在运行的应用程序所建立的所有对象,这些对象通 过new.newarray.anewarray和mul ...

  9. 浅析JAVA的垃圾回收机制(GC)

    1.什么是垃圾回收? 垃圾回收(Garbage Collection)是Java虚拟机(JVM)垃圾回收器提供的一种用于在空闲时间不定时回收无任何对象引用的对象占据的内存空间的一种机制. 注意:垃圾回 ...

随机推荐

  1. ASP.NET MVC3 在_ViewStart設定Layout後用RenderAction的注意事項

    ASP.NET MVC3 在_ViewStart設定Layout後用RenderAction的注意事項 3/24 TW MVC第一次活動圓滿的結束了,雖然是RC,但也來了不少願意聽我們分享的好朋友. ...

  2. python读取xml文件

    关于python读取xml文章很多,但大多文章都是贴一个xml文件,然后再贴个处理文件的代码.这样并不利于初学者的学习,希望这篇文章可以更通俗易懂的教如何使用python 来读取xml 文件. 什么是 ...

  3. iOS-Block的多种使用

    一.图 二.代码 1.viewController.h #import <UIKit/UIKit.h> @interface ViewController : UIViewControll ...

  4. iOS-appStore发布流程

    appStore上传苹果应用程序软件发布流程http://blog.sina.com.cn/s/blog_68661bd801019uzd.html

  5. MySQL中的备份和恢复

    MySQL备份 MySQL中的逻辑备份是将数据库中的数据备份为一个文本文件,备份的文件可以被查看和编辑.在MySQL中,使用mysaldump工具来完成备份.有以下3种来调用mysqldump: 备份 ...

  6. 面向对象的Javascript(4):重载

    在小项目中对于JavaScript使用,只要写几个function就行了.但在大型项目中,尤其是在开发追求 良好的用户体验的网站中,如SNS,就会 用到大量的JavaScrpt,有时JavaScrip ...

  7. WPF后台设置xaml控件的样式System.Windows.Style

    WPF后台设置xaml控件的样式System.Windows.Style 摘-自 :感谢 作者: IT小兵   http://3w.suchso.com/projecteac-tual/wpf-zhi ...

  8. 004_URL 路由 - 定制路由系统 & 使用区域

    定制路由系统 路由系统是灵活可配置的,当然还可以通过下面这两种方式定制路由系统,来满足其他需求. 1.  通过创建自定义的RouteBase实现: 2.  通过创建自定义路由处理程序实现. 创建自定义 ...

  9. sql server 2008出现评估期已过的问题

    我的sql server2008用来半年吧,那天的昨天还能用,到了180天后,就不能用了,具体问题如下: 出了这个问题后,就打不开sql server了 解决方法: 1.打开安装中心,升级sql se ...

  10. 不可或缺 Windows Native (5) - C 语言: 数组

    [源码下载] 不可或缺 Windows Native (5) - C 语言: 数组 作者:webabcd 介绍不可或缺 Windows Native 之 C 语言 数组 示例cArray.h #ifn ...