http://www.cnblogs.com/xingzc/p/5756119.html
http://www.cnblogs.com/redcreen/archive/2011/05/04/2037057.html
java中,栈的大小通过-Xss来设置,当栈中存储的数据比较多时,需要适当调大这个值,否则会出现 java.lang.StackOverflowError异常
1.数据类型
2.堆与栈
(1)为什么要把堆和栈区分出来呢?栈中不是也可以存储数据吗?
(2)在java中,Main函数就是栈的起始点,也是程序的起始点。
(3)堆中存什么?栈中存什么?
(4)java中的参数传递是传值呢?还是传引用?
(5)java对象的大小
(6)引用类型: 对象引用类型分为强引用、软引用、弱引用和虚引用
(7)按照基本回收策略分
引用计数(Reference Counting)
标记-清除(Mark-Sweep)
复制(Copying)
标记-整理(Mark-Compact)
(8)按分区对待的方式分
增量收集
分代收集: 年轻代、年老代、持久代
(9)按系统线程分:
串行收集: 串行收集使用单线程处理所有垃圾回收工作
并行收集: 并行收集使用多线程处理垃圾回收工作
并发收集: GC线程和应用线程大部分时间是并发执行
(10)如何区分垃圾
垃圾回收的起点是一些根对象(java栈、静态变量、寄存器...)。而最简单的java栈就是java程序执行的main函数。这种回收方式,也是上面提到的“标记-清除”的回收方式。
(11)如何处理碎片
“复制”方式和“标记-整理”方式,都可以解决碎片的问题
(12)如何解决同时存在的对象创建和对象回收问题
垃圾回收线程是回收内存的,而程序运行线程则是消耗(或分配)内存的
要进行垃圾回收前,一般都需要暂停整个应用(即:暂停内存的分配),然后进行垃圾回收,回收完成后再继续应用
这种方式有一个很明显的弊端,就是当堆空间持续增大时,垃圾回收的时间也将会相应的持续增大,相应应用暂停的时间也会相应的增大
并发垃圾回收算法
(13)为什么要分代
不同的对象的生命周期是不一样的。因此,不同声明周期的对象可以采取不同的收集方式,以便提高回收效率。
分代垃圾回收采用分治的思想,进行代的划分,把不同生命周期的对象放在不同代上,不同代上采用最适合它的垃圾回收方式进行回收。
(14) 如何分代
虚拟机中共划分了三个代:年轻代(Young Generation)、年老代(Old Generation)和持久代(Permanent Generation)。
年轻代:年轻代的目标就是尽可能快速的收集掉那些生命周期短的对象。
年轻代分为三个区。一个Eden区,两个Survivor(幸存者)区
年老代:可以认为年老代中存放的都是一些生命周期较长的对象
持久代:用于存放静态文件,如java类、方法等。持久代对垃圾回收没有显著影响
持久代大小通过 -XX:MaxPermSize = 进行设置
(15)什么情况下触发垃圾回收
GC有两种类型:Scavenge GC 和 Full GC
Scavenge 清除污物;打扫
Scavenge GC: 一般情况下,当新对象生成,并且在Eden申请空间失败时,就会触发Scavenge GC
Full GC: 对整个堆进行整理,包括Young、Tenured 和 Perm。应该尽可能减少 Full GC 的次数
在对JVM调优的过程中,很大一部分工作就是对于 Full GC 的调节。
(16) 有如下原因可能导致Full GC:
年老代(Tenured)被写满
持久代(Perm)被写满
System.gc()被显式调用
上一次GC之后Heap的各域分配策略动态变化
(17) 分代垃圾回收流程示意
(18) 选择合适的垃圾收集算法
串行收集器: 可以使用 -XX:+UseSerialGC打开。
并行收集器:
对年轻代进行并行垃圾回收,因此可以减少垃圾回收时间。一般在多线程多处理器机器上使用
使用 -XX:+UseParallelGC 打开
可以对年老代进行并行收集, 使用 -XX:+UseParallelOldGC打开。
使用 -XX:ParallelGCThreads = 设置并行垃圾回收的线程数。此值可以设置与机器处理器数量相等
并发收集器: 此收集器适合对响应时间要求比较高的中、大规模应用。
使用 -XX:+UseConcMarkSweepGC打开
并发收集器使用处理器换来短暂的停顿时间。
在一个N个处理器的系统上,并发收集部分使用 k/N 个可用处理器进行回收,
一般情况下 1 <= k <= N / 4。
(19) 浮动垃圾
由于在应用运行的同时进行垃圾回收,所以有些垃圾可能在垃圾回收进行完成时产生,这样就造成了“Floating Garbage”
并发收集器一般需要20%的预留空间用于这些浮动垃圾。
(20) Concurrent Mode Failure
并发收集器在应用运行时进行收集,所以需要保证堆在垃圾回收的这段时间有足够的空间供程序使用,否则,垃圾回收还未完成,堆空间先满了
(21)启动并发收集器
通过设置 -XX:CMSInitiatingOccupancyFraction = 指定还有多少剩余堆是开始执行并发收集。
(22)小结
串行处理器:
-- 适用情况:数据量比较小(100M左右),单处理器下并且对相应时间无要求的应用。
-- 缺点:只能用于小型应用。
并行处理器:
-- 适用情况:“对吞吐量有高要求”,多CPU,对应用过响应时间无要求的中、大型应用。举例:后台处理、科学计算。
-- 缺点:垃圾收集过程中应用响应时间可能加长。
并发处理器:
-- 适用情况:“对响应时间有高要求”,多CPU,对应用响应时间有较高要求的中、大型应用。举例:Web服务器/应用服务器、电信交换、集成开发环境。
3. 堆大小设置
(1)年轻代的设置很关键
JVM中最大堆大小有三方面限制:相关操作系统的数据模型(32-bit 还是64-bit)限制;系统的可用虚拟内存限制;系统的可用物理内存限制。
32位系统下,一般限制在1.5G~2G;64位操作系统对内存无限制。在Windows Server 2003系统,3.5G物理内存,JDK5.0下测试,最大可设置为1478m
(2) 典型设置:
java -Xmx3550m -Xms3550m -Xmn2g -Xss128k
-Xmn2g: 设置年轻代大小为2G。整个堆大小=年轻代大小+年老代大小+持久代大小。
持久代一般固定大小为64m,所以增大年轻代后,将会减小年老代大小。
此值对系统性能影响较大,Sun官方推荐配置为整个堆的3/8。
4. 回收器选择:
(1) JVM给了三种选择:串行收集器、并行收集器、并发收集器,但是串行收集器只适用于小数据量的情况
JDK5.0以后,JVM会根据当前系统配置进行判断
(2) 吞吐量优先的并行收集器典型配置:
并行收集器主要以到达一定的吞吐量为目标,适用于科学计算和后台处理等。
java -Xmx3800m -Xms3800m -Xmn2g -Xss128k -XX:+UseParallelGC -XX:ParallelGCThreads=20
-XX:+ParallelGCThreads=20:配置并行收集器的线程数,
即:同时多少个线程一起进行垃圾回收。此值最好配置与处理器数目相等。
-XX:+UseParallelOldGC:配置年老代垃圾收集方式为并行收集。JDK6.0支持对年老代并行收集
(3) 响应时间优先的并发收集器,典型配置:
并发收集器主要是保证系统的响应时间,减少垃圾收集时的停顿时间。适用于应用服务器、电信领域等
java -Xmx3550m -Xms3550 -Xmn2g -Xss128k -XX:ParallelGCThreads=20 -XX:+UseConcMarkSweepGC -XX:+UseParNewGC
5. 常见配置汇总
堆设置
-Xms:初始堆大小
-Xmx:最大堆大小
-XX:NewSize=n:设置年轻代大小
-XX:NewRatio=n:设置年轻代和年老代的比值。如:为3,表示年轻代与年老代比值为1:3,表示Eden:Survivor=3:2,一个Survivor区占整个年轻代的1/5。
-XX:MaxPermSize=n:设置持久代大小
收集器设置
-XX:+UseSerialGC:设置串行收集器
-XX:+UseParallelGC:设置并行收集器
-XX:+UseParalledlOldGC:设置并行年老代收集器
-XX:+UseConcMarkSweepGC:设置并发收集器
垃圾回收统计信息
-XX:+PrintGC
-XX:+PrintGCDetails
-XX:+PrintGCTimeStamps
-Xloggc:filename
并行收集器设置
-XX:ParallelGCThreads=n:设置并行收集器收集时使用的CPU数。并行收集线程数。
-XX:MaxGCPauseMillis=n:设置并行收集最大暂停时间
-XX:GCTimeRatio=n:设置垃圾回收时间占程序运行时间的百分比。公式为1/(1+N)
并发收集器设置
-XX:+CMSIncrementalMode:设置为增量模式。适用于单CPU情况。
-XX:+ParallelGCThreads=n:设置并发收集器年轻代收集方式为并行收集时,使用的CPU数。并行收集线程数
阅读(677) | 评论(0) | 转发(0) |