java性能调优权威指南读书笔记六(JVM性能调优)

来源:互联网 发布:画设备流程图软件 编辑:程序博客网 时间:2024/06/05 08:19

基本方法

   首先要明确一点,当性能的优化已经到达JVM调优的层级,请先确保在代码以及数据结构的层面已经对于应用进行了足够的优化。其次,JVM的优化内容已经相对比较底层,其优化的细节更多的是满足于应用对于某一个或者是某几个方面性能的要求,并且这些优化的实现往往伴随着其余一个或多个方面的性能牺牲或者是硬件的以及软件的升级。
在JVM调优的时候需要明确调优的需求,之后需要选择JVM的部署模式、可用性、可管理性、以及内存使用,之后就是JVM运行时环境,垃圾收集器调优,在每个步骤中都通过多次的迭代最终达到一个满足应用需求的性能体现。

需求分析

可用性:可用性指的是当发生意外事故,机器故障等情况时,应用还能够在多大程度上提供服务。
可管理性:用以描述应用在使用维护过程中的操作性开销的度量
吞吐量:吞吐量是应用在单位时间内的处理任务的数量,一般用来描述应用对于任务处理的能力,一般来说增加吞吐量的代价是延迟的增加或内存使用的增加。
延迟及响应性:延迟或者是响应是对应用程序 指令开始工作到完成工作的时间消耗
内存占用:值在同等吞吐量延迟可用性和管理性的前提下运行应用程序需要的内存大小
启动时间:程序初始化需要的时间消耗

JVM部署模式

单一JVM部署模式:使用一个JVM进行服务的提供,极大的降低了管理的成本,但是同时也极大的降低了可用性
多JVM部署模式:将应用部署到多个JVM实例上可以获得更好的可用性,以及低延迟的可能性。采用多JVM部署的时候单个失效只会影响部分的功能。并且可以将不同JVM绑定到处理器集可以避免由于应用程序线程被分别帮到到不同CPU缓存引起的跨硬件线程迁移。
JVM运行模式
Client以及Server模式,名字已经说明的非常清楚了一种是面向桌面应用的模式,目的是减少用户的等待时间,一种是服务器端的应用模式,目的是使得在服务器稳态的时候有比较好的性能表现。所以在Client模式中会减少JVM开始的优化,将更多的处理放置在操作过程中。而对应的在Server模式中,将会有大量的优化在服务开始前被完成,这能保证服务提供的质量和速度。

 垃圾收集器调优

HotSpot提供多个垃圾收集器可以选择:Serial收集器、Throughput收集器、Mostlu-Concurrent收集器以及G1收集器,将会需要根据需要实现的性能进行选择和调整。
以下是垃圾收集器调优的几个原则:
1每次Minor都尽可能的收集垃圾对象,因为相对来说Full GC不论在哪种状态下持续时间总是最长的,Full GC的超长停顿往往是无法到达延迟或吞吐量的要求的罪魁祸首
2处理吞吐量和延迟问题,能够使用的内存越大,堆空间越大,垃圾收集器的效果越好,应用也就越流畅
3在这三个吞吐、延迟、内存占用中一般选两个进行优化

内存占用调优

于其他两项的调优情况不同的是,内存调优值得是获取到应用详细的内存使用情况以及信息,并制定出合适的内存占用策略,而不是缩减内存的使用,也即内存调优是一种手段,而之后的延迟调优以及吞吐量调优都是目的。
首先要了解目标应用的环境情况,物理机的属性情况,机器上JVM的部署数量,物理机的使用情况(独占、共用),注意在这里无论如何都需要考虑给予操作系统预留的内存余量。

HotSpot VM堆的布局

HotSpot的三个主要的堆空间划分为:新生代、老年代、永久代
在JVM的参数中可以通过-Xms 和Xmx设置新生代+老年代大小的最小值和最大值,在JVM运行过程中大小可以进行动态的自动调整。但是一般来说如果应用对于吞吐量以及延迟有要求的话,那么两个值设置为一样比较妥当,这是由于在调整大小的时候都需要Full GC伴随,这个性能影响较大。
可以通过-Xmn来设置新生代的大小。老年代的大小将会根据之前的设置隐式可计算。
同样永久代的大小也能通过对应的设置,但是保持永久代大小一致也是有意义的。
在调优的时候有个最重要的知识点,即在新生代、老年代、永久代任意内存空间不能满足应用的内存请求的时候FULL GC将会被触发,而FULL GC是长停顿并且性能消耗极大的操作,正是对于垃圾收集器调优的重点。

堆大小调优的着眼点

堆大小调优的目的是在应用处于稳态的时候体现出更好的性能,减少Full GC对于应用的影响。通过在从测试的时候抓取GC日志观察垃圾收集器的工作情况,并且调整应用JVM的内存从小到大,通过在日志中查看是否出现了outOfMemoryError来判断,并缓慢增加JVM内存的大小,一直迭代此过程直到不再出现outOfMemoryError,下一步就能开始统计应用程序中的活跃数据大小了。

计算活跃数据大小

活跃数据指的是应用处于稳定状态时常去存活在java堆中占用空间的大小,其组成包括老年代占用java堆大小,永久代占用java堆大小。为了能够正确的估计出活跃数据大小,需要在测定之前进行多次主动的Full GC来收集垃圾(通过命令或者相关的应用都可以实现)。

初始堆空间大小配置

  一般来说我们可以通过仅需多次Full GC稳定运行的应用获取平均的应用java堆占有量。
一般来说存在以下的几条通用的法则
    1java堆的初始值-Xms和最大值-Xmx设置为老年代活跃数据大小的3~4倍左右
    2永久带的初始值-XX:PermSize以及最大值-XX:MaxPerSize应该比永久带活跃的数据大1.2~1.5倍,这个是由于永久带的数据一旦溢出会出现错误。
    3新生代空间应该为蓝年代空间活跃数据的1~1.5倍
阅读全文
0 0
原创粉丝点击