JVM 年轻代和年老代 大小设置_设置年轻代大小_追寻北极的博客-程序员宝宝

技术标签: base  

有许多现成的调优经验的介绍。Charlie Hunt写的《Java Performance》一书里有很详细的介绍。 中文版就快出了,敬请关注。 
其中涉及GC调优的部分在过往的JavaOne里也有session介绍过。请搜这个标题:"Step-by-Step: Garbage Collection Tuning in the Java HotSpot Virtual Machine" 

不过那种很具体的现成经验毕竟是别人在他们见过的环境里沉淀下来的,并不一定适用于所有情况。所以怎样的调优方法适合自己,还是得理解了系统底层的工作原理然后再在实际环境里加以应用、变通才好。 

对HotSpot VM里的GC不熟悉的,至少应该把 Sun以前出的HotSpot VM的GC调优白皮书读了。 

==================== 

为啥HotSpot VM里收集有两种概念,一种是young GC/minor GC,另一种是full GC/major GC;为啥后者不是叫old GC? 

JVM <wbr>年轻代和年老代 <wbr>大小设置
因为young GC只收集young gen,但full GC会收集整个GC堆。 
HotSpot VM的full GC会收集整个Java堆,包括其中的young gen与old gen;同时也会顺便收集不属于Java堆的perm gen。 
Young + old + perm构成了HotSpot VM的整个GC堆。至少目前还是这样。 
(JDK8里的HotSpot VM就没有perm gen了。请注意。) 

CMS在并发模式工作的时候是只收集old gen的。但一旦并发模式失败(发生concurrent mode failure)就有选择性的会进行全堆收集,也就是退回到full GC。 

==================== 

大小分配怎样才合理取决于某个具体应用的对象的存活模式。 

这涉及到分代式GC的原理。最初为何要把GC堆划分为多个区域,以不同的频率来收集它们?本来就是为了让每次收集的效率都最大(在收集的区域里尽可能回收出可用空间)。如果一个应用里对象的存活模式满足弱分代假设,那么把新生对象放在同一个区域里,每次收集这个区域的效率都应该比较高(因为假设是新生对象活不了多久就死了)。 

有人专门研究这个。可以用"java object demography"这组关键字来搜已有资料。 

==================== 

举例:可能很多人都有一种印象,young gen应该比old gen小。笼统说确实如此,因为在最坏情况下young gen里可能所有对象都还活着,而如果它们全部都要晋升到old gen的话,那old gen里的剩余空间必须能容纳下这些对象才行,这就需要old gen比young gen大(否则young GC就无法进行,而必须做full GC才能应付了)。 
实际上却不总是这样的。所谓“最坏情况”在很多系统里是永远不会出现的。调优就是要针对实际应用里对象的存活模式来破除这些“最坏情况”的假设带来的限制。 

许多Web应用里对象会有这样的特征: 
·(a) 有一部分对象几乎一直活着。这些可能是常用数据的cache之类的 
·(b) 有一部分对象创建出来没多久之后就没用了。这些很可能会响应一个请求时创建出来的临时对象 
·(c) 最后可能还有一些中间的对象,创建出来之后不会马上就死,但也不会一直活着。 


如果是这样的模式,那young gen可以设置得非常大,大到每次young GC的时候里面的多数对象(b)最好已经死了。 
想像一下,如果young gen太小, 每次满了就触发一次young GC,那么young GC就会很频繁,或许 很多临时对象(b)正好还在被是使用(还没死),这样的话young GC的收集效率就会比较低。要避免这样的情况,最好是就是把 young gen设大一些。 

那old gen怎么办?如果是上面说的情况,那old gen至少要足以装下所有长期存活的对象(a);同时也要留出一定的余地用来容纳 young GC没能清理掉的临时对象。 

这样,最后调整出来的结果很可能y oung GC反而比old gen大许多。这完全没问题。 

只有(a)和(b)的话就完美了,现实中最头疼的就是针对(c)对象的调优。它们或许会经历多次young GC之后仍然存活,于是晋升到old gen;但晋升上去之后或许很快就又死掉了。 
这种对象 最好能不让晋升到old gen(可以让它们在survivor space里多来回倒腾几次再晋升,也就是想办法增加 tenuring threshold;不过HotSpot VM里的GC不让外界对此多插手,想减小MaxTenuringThreshold很容易,想增加实际有效的tenuring threshold就没那么容易了)。但如果真的不让它们晋升,young GC的暂停时间就会增长(在survivor space里来回倒腾对象意味 着要来回拷贝,这会花时间)。 
所以有一种策略是尽量让这种对象的 大部分在young GC中消耗掉(在保持young GC的暂停时间不超过某个预期值的前提下),而“漏”到old gen的那些让诸如 CMS之类的并发GC来解决。 
总之这里要做一定的tradeoff就是了。 

================= 

知道了原理之后在现实中要如何实践呢? 

首先得了解硬性限制: 某个服务器总共有多少内存,其中最多可以分配多少给某个应用程序;有没 有一些服务对响应时间有严格要求,有的话限制是多少,之类的。 

然后看看应用的特征是怎样的。可以借助一些工具来了解对象的存活情况,例如NetBeans的 profiler就有这样的功能( 老文档);许多其它主流Java profiler也有类似的功能。 
这些工具的精度和性能开销各异,总之自己摸索下看看吧。 

情况了解清楚了就可以开始迭代调整各种参数看实际运行的表现如何。迭代到满意为止。 
要分析实际GC的运行状况,首要切入点就是 分析GC日志。有很多工具能把HotSpot VM的GC日志可视化。我以前一直在用的是这个: GCHisto。 
然后像Twitter做的这个工具也可以抽取一些GC的辅助统计信息: https://github.com/twitter/jvmgcprof 

================= 

那个…上面随便写了些。文字不通顺的地方请轻拍,要整理成“文章”的话又要烧脑细胞了… 

没说清楚的地方请另外补充背景知识… 
例如这个: http://www.infoq.com/interviews/szegedi-performance-tuning,Attila Szegedi的GC调优经验。 
还有这个: http://www.infoq.com/presentations/Understanding-Java-Garbage-Collection,Gil Tene谈GC。
   

如果老年代设置过小,就会频繁触发full gc,full gc是非常耗时的。年轻代在经过n(hotspot默认是15)轮后会进入老年代,这样老年代顶不住了,就会触发full gc,回收时需要stop the world,这样系统经常发生长时间停顿,影响系统的吞吐量




原文地址:http://blog.sina.com.cn/s/blog_4adc4b090102vr1v.html

版权声明:本文为博主原创文章,遵循 CC 4.0 BY-SA 版权协议,转载请附上原文出处链接和本声明。
本文链接:https://blog.csdn.net/joeyon/article/details/78606748

智能推荐

python 面向对象编程tcp_python面向对象、类、socket网络编程_weixin_39911916的博客-程序员宝宝

类和对象python3统一了类与类型的概念;类==类型;从一组对象中提取相似的部分就是类;特征与技能的结合体就叫做对象;类的功能:初始实例化;属性引用;1、数据属性;2、函数属性;对于一个实例来说,只一种功能:属性引用;示例:class Garen:camp = 'Demacia'def __init__(self,nickname,aggresivity,life_value):self.nic...

软件构造 Lab3_哈工大2019软件构造lab3实验报告_LanHBSan的博客-程序员宝宝

实验目的:本次实验覆盖课程第 3、5、6 章的内容,目标是编写具有可复用性和可维护 性的软件,主要使用以下软件构造技术: 子类型、泛型、多态、重写、重载 继承、代理、组合 常见的设计模式 语法驱动的编程、正则表达式 基于状态的编程 API 设计、API 复用本次实验给定了五个具体应用(径赛方案编排、太阳系行星模拟、原子结构 可视化、个人移动 App 生态系统、个人社交系...

STFT振动信号Python实践_AaronCosmos的博客-程序员宝宝

使用Python中Scipy库对轴承振动信号做离散STFTfrom scipy import signalimport matplotlib.pyplot as pltimport numpy as npimport pandas as pd%matplotlib inlinepath_all='D:\\15_07_10\\' data = pd.read_csv(path_all...

python摄像头识别条形码、二维码并打印信息_工业相机 python ai识别和扫码_cwqHHH的博客-程序员宝宝

提前安装好pyzbar 和 opencv-python库//安装方法:打开cmd, 输入 pip install ...(pyzbar / opencv-python)注意!!!打开摄像头的瞬间,不要被自己的大脸吓到哈哈哈哈哈哈哈哈哈#首先导入本次所需要的库,最后一个csv是Python自带的csv表格操作库,这里我们需要把我们扫到的二维码信息都存入csv表格里。import ...

li标签和a标签的点击时间如何同时触发(涉及JS的默认事件,冒泡,捕获)_点击a标签触发时间_悟道|养家的博客-程序员宝宝

参考作者献上:http://caibaojian.com/javascript-stoppropagation-preventdefault.html页面中的所有#menus1 li 都绑定了click()事件,需求是当点击&lt;li&gt;菜单的时候触发&lt;li&gt;以及&lt;li&gt;下的&lt;a&gt;标签的点击时间,&lt;li&gt;click是给&lt;li&gt;加class标记被选择,&lt;a&gt;标签click是打开页面,遇到问题是,&lt;a&gt;标签的事件触

npm install 出现 unable to resolve dependency tree_BrightSunshine°的博客-程序员宝宝

项目场景:npm install 出现 unable to resolve dependency tree问题描述:在rn中下载第三方库时候出现 unable to resolve dependency tree:npm ERR! code ERESOLVEnpm ERR! ERESOLVE unable to resolve dependency treenpm ERR!npm ERR! While resolving: [email protected] ERR! Foun

随便推点

apicloud 打开新页面并关闭当前页面方法_奋斗在前端的实习小白的博客-程序员宝宝

// 监听页面消失的时候,关掉页面就可以了 api.addEventListener({ name:'viewdisappear' },function(){ api.closeWin(); });内容发放为转载;原文作者:https://www.cnblogs.com/jiqing9006...

SpringSecurity认证基本原理与认证2种方式_spring security 多种认证_程序小黑马的博客-程序员宝宝

2.1 HttpBasic认证2.2 &nbsp;formLogin登录认证模式2.3 表单认证2.3.1 在config包下编写SecurityConfiguration配置类2.3.2 解决静态资源被拦截问题改造登录2.4 基于数据库实现认证功能2.5 密码加密验证Spring Security功能的实现主要是由一系列过滤器相互配合完 成。也称之为过滤器链,Spring Security默认加载15个过滤器, 但是随着配置可以增加或者删除一些过滤器.一、过滤器链介绍image-2021112415505

C++ 条件运算符(?:)= if else_小黄TimTim仔的博客-程序员宝宝

?:运算符(条件运算符)?:运算符用来代替if else语句,在C++中唯一一个需要三个操作数的运算符。格式:条件1 ?条件2 : 条件3使用方法:若条件1为真,则结果取条件2若条件1为假,则结果取条件3eg:5&gt;3 ? 10 : 12 解释:5&gt;3为真,所以结果为10;3 == 9 ? 10 :12 解释:3==9为假,所以结果为12;与if else语句等效eg:int c = a &gt; b ? a : b;相同于int c;if(a &gt; b...

小程序button按钮样式及授权_暖光_&的博客-程序员宝宝

小程序button按钮狂傲样式,在wxss中无效果,可以在style重写样式&lt;button open-type="getUserInfo" bindgetuserinfo="callUser" style="width:80%;line-height:88rpx;height:88rpx;padding:0" class="btn" &gt;授权登录&lt;/button&gt;o...

【图像处理】自动白平衡(AWB)_awb plots_gangeqian2的博客-程序员宝宝

参考 https://blog.csdn.net/lg1259156776/article/details/52012265