6. 垃圾收集GC
(1)当需要排查各种内存溢出,内存泄漏等问题,当GC成为系统达到更高性能的瓶颈时,我们就需要对这些自动化的GC进行监控和调节。

(2)PC计数器、本地方法栈、虚拟机栈,随方法或者线程的结束而消亡,所以不用考虑回收其内存。内存回收的主要区域是 堆Heap 和 方法区。

(3) 垃圾收集器,在回收对象前需要判断对象是否还存活,判断对象是否存活方法:

a.引用计数算法: 给对象添加一个引用计数器,每当有一个地方引用它时,计数器值就+1;当引用失败时,计数器值就-1。
任何时刻,计数器值为0的对象就是不可能被再使用的。
优点:实现简单,效率高
缺点:很难解决对象之间相互引用的问题。如GcBean里面的问题。(两个在堆上的对象相互引用,但是他们的句柄都指向了null,
已经没有句柄指向他们,所以这两个对象不会再被用到,但是,因为他们之间相互引用,所以不会被垃圾回收。

b.可达性分析算法(Reachability Analysis): 思路,通过一系列称为 "GC Roots"的对象,作为起始点,从这些节点开始向下
搜索,搜索走过的路径称为引用链(Reference Chain),当一个对象到GC Roots 没有任何引用链时,则证明这个对象是不可用的。
可以被垃圾收集器回收的。

----------------------------------------------------------
| ---------- |
| |GC Roots| |
----------------------------------------------------------
|
|
--------- ----------
| obj1 | | obj3 |
--------- ----------
| |
| |
--------- ----------
| obj2 | | obj4 |
--------- ----------

如图obj1和obj2是可用对象,不会被GC回收;
obj3和obj4虽然他们之间有联系,但是,他们到GC Roots 不可达,所以,他们将会判定为不可回收对象。

c.在java中可作为GC Roots的对象的有:
I.虚拟机栈中引用的对象。
II.方法区中类静态属性引用的值。
III.方法区中常量引用的对象
IV.本地方法栈中 JNI(即一般说的native方法) 引用的对象。

(4)回收堆
I. 对象在经过可达性分析后,发现没有与GC Roots相关联的引用链,它将会被第一次标记(标记此对象没有引用链),并且进行一次筛选,此对象是否有必要执行finalize()方法。
II. 筛选的条件是: 此对象是否有必要执行finalize()方法,
当对象没有覆盖finalize()方法,或者对象的finalize()方法被虚拟机掉用过,虚拟机将这两种情况都视为,没有必要执行。
III. 如果对象被虚拟机判定有必要执行finalize()方法时,那么对象会被放置在一个叫做F-QUEUE的队列当中,稍后会有一个虚拟机
建立的,优先级低的Finalizer线程去执行它。
IV. finalize()方法,是对象逃脱被回收的最后一次机会,如果对象在finalize方法中重新与GC Roots上的任何一个对象关联上,
那么GC在第二次标记时,将把这个对象移除“即将回收集合”;如果对象这是还没有逃脱,那它就基本被回收了。
V. 需要注意一点,每个对象的finalize()方法只会被JVM执行一次,如果对象通过finalize()方法逃出过被回收一次,那么就不会
有第二次。
finalize()应尽量避免使用,运行代价高昂,不确定性大,无法保证各个对象的调用顺序。
(5)回收方法区
永久代的垃圾收集主要回收两部分内容:废弃常量和无用的类。
I.常量池中有(类、接口、方法、字段的符号引用,字符),判断一个常量是否是废弃常量比较简单,有没有对象引用常量,如果没有其他地方引用
了这个常量,如果这是发生内存回收,而且必要的话,这个常量就会被回收。
II.无用的类:
a. 加载类的ClassLoader已经被回收
b. 该类的所有实例都已经被回收,即java堆中不存在该类的任何实例。
c.无法在任何地方通过反射访问该类。
满足这三个条件,类就可以被回收。Hotspot虚拟机,提供, -Xnoclassgc 参数控制。

(6)垃圾收集算法
I. 标记-清除(Mark-Sweep)算法:
a.标记出所有需要被回收的对象
b.标记完成后,统一回收被标记的对象。
缺点: 效率问题,标记和清除两个过程效率都不高。
空间问题,标记清除之后会产生大量不连续的内存碎片,可能会导致以后要分配大内存对象时,无法找到足够的连续内存,而不得不
触发另一次垃圾收集动作。

II. 复制(Copying)算法:HotSpot虚拟机
a. 将用内存按容量划分为大小相等的两块,每次只使用其中的一块,当这一块内存用完了,就将还存活的对象复制到另外一块内存,然后把
使用过的空间,一次性清除掉。
优点:实现简单,运行高效
缺点: 内存缩小成原来的一般,影响性能。

b. 新生代中的对象98%是 朝生夕死,所以不需要按照1:1的比例来划分内存空间。而是将 新生代内存 分为一块较大的Eden空间和两块较小的Suvivor空间,
每次使用Eden和其中一块的Survivor;
当回收时,将Eden区和Survivoe区的存活对象,一次性复制到另外一块Survivor区,清理Eden区,和刚才用过的Survivor空间。
Eden区和Survivor区占比:Eden:S1:S2 = 8:1:1 , 即每次新生代中可用内存空间为整个内存空间的 (1+8 ):1 = 90% ,
c.如果Survivor区空间不够用时,需要依赖 老年代 进行分配担保机制,把对象分配到老年代。

III. 标记-整理 算法:
a.标记出所有需要被回收的对象
b.标记完成后,让所有的存活对象向一端移动,然后清理掉边界意外的内存区域。

IV. 分代收集(Generation Collection) 算法
分代收集没有新东西,根据对象存活周期不同,把对象分为几部分。

a. 把java堆分为老年代和新生代,新生代使用复制算法(Eden , Suvivor1 , Suvivor2 ),
b.老年代因为对象存活率高,没有更多的内存使用复制算法收集,所以,使用 标记-清除,或者使用 标记-整理算法 进行垃圾回收。
(7) 垃圾收集器
I.http://blogs.sun.com
Serial ParNew CMS Serial Old GI ..

(8) Full GC 和 Minor GC
I.新生代GC ,Minor GC ,指发生在新生代的垃圾收集动作,因为java对象大多都是朝生夕死,所以Monor GC非常频繁,一般回收速度也比较快。
II.老年代GC ,FULL GC ,发生在老年代的GC ,一般比新生代GC慢十倍以上。

(9) 内存分配策略:
I.对象优先在Eden区分配。
II.大对象直接进入老年代(很长的字符串,或者数组byte[]),老年代垃圾回收比较慢,所以应尽量少使用大对象(还有短大对象)。
-XX:PretenureSizeThreshold ,参数,大于此参数值的对象进入老年代。
III.长期存活的对象进入老年代。

jvm--4垃圾收集的更多相关文章

  1. 深入理解JVM(5)——垃圾收集和内存分配策略

    1.垃圾收集对象 垃圾收集主要是针对堆和方法区进行. 程序计数器.虚拟机栈和本地方法栈这三个区域属于线程私有的,只存在于线程的生命周期内,线程结束之后也会消失,因此不需要对这三个区域进行垃圾回收. 哪 ...

  2. JVM中垃圾收集算法总结

      通过前面的介绍我们了解了对象创建和销毁的过程.那么JVM中垃圾收集器具体对对象回收采用的是什么算法呢?本文主要记录下JVM中垃圾收集的几种算法. JVM的垃圾回收的算法 标记-清除算法(Mark- ...

  3. Java 7 JVM和垃圾收集

    ---恢复内容开始--- 写JAVA程序,一定要了解JVM(JAVA Virtual machine)一些基础知识和垃圾收集.如果对JVM已经很了解了,可以不用继续往下阅读了.本文只针对Java 7, ...

  4. JVM之垃圾收集器

    前一篇讲了垃圾收集算法--JVM之GC算法.垃圾收集算法——标记-清除算法.复制算法.标记-整理算法.分代收集算法,如果把它看作是方法论,那么下面说的就应该是内存回收的具体实现. 先看一下JVM中有哪 ...

  5. 【转载】JVM 学习——垃圾收集器与内存分配策略

    本文主要是对<深入理解java虚拟机 第二版>第三章部分做的总结,文章中大部分内容都来自这章内容,也是博客 JVM 学习的第二部分. 简述 说到垃圾收集(Garbage Collectio ...

  6. JVM、垃圾收集器

    1.Java虚拟机原理 所谓虚拟机,就是一台虚拟的机器.他是一款软件,用来执行一系列虚拟计算指令,大体上虚拟机可以分为系统虚拟机和程序虚拟机, 大名鼎鼎的Vmare就属于系统虚拟机,他完全是对物理计算 ...

  7. JVM之垃圾收集器与内存分配回收策略(二)

    上一篇JVM垃圾收集器与内存分配策略(一),下面是jdk1.7版本的垃圾收集器之间的关系,其中连线两端的两种垃圾收集器可以进行搭配使用,下面来总结一下这些收集器的一些特点以及关系. 一.Serial收 ...

  8. 理解JVM之垃圾收集器详解

    前言 垃圾收集器作为内存回收的具体表现,Java虚拟机规范并未对垃圾收集器的实现做规定,因而不同版本的虚拟机有很大区别,因而我们在这里主要讨论基于Sun HotSpot虚拟机1.6版本Update22 ...

  9. 理解JVM之垃圾收集器概述

    前言 很多人将垃圾收集(Garbage Collection)视为Java的伴生产物,实际1960年诞生的Lisp是第一门真正使用内存动态分配与垃圾手机技术的语言.在目前看来,内存的动态分配与内存回收 ...

  10. JVM各垃圾收集器对比

    本随笔是<深入理解Java虚拟机 JVM高级特性与最佳实践>读书笔记. 1.JDK1.7之后的HotSpot虚拟机所包含的所有收集器如下: 解读: 1. 总共有7种垃圾收集器 2.Seri ...

随机推荐

  1. python爬虫学习(6) —— 神器 Requests

    Requests 是使用 Apache2 Licensed 许可证的 HTTP 库.用 Python 编写,真正的为人类着想. Python 标准库中的 urllib2 模块提供了你所需要的大多数 H ...

  2. java 多线程 Synchronized方法和方法块 synchronized(this)和synchronized(object)的理解

    synchronized 关键字,它包括两种用法:synchronized 方法和 synchronized 块. 1. synchronized 方法:通过在方法声明中加入 synchronized ...

  3. 初识WebService

    一.什么是Web服务 Web服务是一种可以用来解决跨网络应用集成问题的开发模式,目的是保证不同平台的应用服务可以互操作 二.Web服务的三个核心 Soap: SOAP(Simple Object Ac ...

  4. UNITY自带的PACKAGE的UTILITY 里面有一个自带的FPS COUNTER

    UNITY自带的PACKAGE的UTILITY 里面有一个自带的FPS COUNTER 可用,但是脚本是保密的?

  5. jdbc java数据库连接 9)事务编程

    1. 事务 基本概念: 事务使指一组最小逻辑操作单元,里面有多个操作组成. 组成事务的每一部分必须要同时提交成功,如果有一个操作失败,整个操作就回滚. 事务ACID特性: l 原子性(Atomicit ...

  6. 使用SQLiteOpenHelper的onUpgrade实现数据库版本升级

    Andoird的SQLiteOpenHelper类中有一个onUpgrade方法.帮助文档中只是说当数据库升级时该方法被触发.经过实践,解决了我一连串的疑问: 1. 帮助文档里说的"数据库升 ...

  7. 关于EventEmitter的用法

    EventEmitter的基本用法: var EventEmitter = require("events").EventEmitter; var ee = new EventEm ...

  8. 那些年我们学过的构造函数(构造方法,C#)

    构造函数也称构造方法,在面向对象中称为构造方法,在面向过程中称为构造函数;C#是面向对象的语言,所以以下都称为构造方法, OK,下面我们先看一下什么是构造函数 class Dog { //创建一个狗类 ...

  9. C#进阶系列——WebApi 异常处理解决方案

    前言:上篇C#进阶系列——WebApi接口传参不再困惑:传参详解介绍了WebApi参数的传递,这篇来看看WebApi里面异常的处理.关于异常处理,作为程序员的我们肯定不陌生,记得在介绍 AOP 的时候 ...

  10. mysql-5.7.11-winx64.zip 安装配置

    1.下载 http://cdn.mysql.com//Downloads/MySQL-5.7/mysql-5.7.11-winx64.zip 2.解压缩zip包: D:\Program Files\m ...