本文转载自ImportNew - 郑雯

每个Java程序员迟早都会碰到下面这个错误:

  • java.lang.OutOfMemoryError

这个时候一般会建议采用如下方式解决这个错误:

  • 增加MaxPermSize值
  • 增加最大堆内存到512M(-xmx参数)

这篇文章会具体介绍Java堆空间和参数MaxPermSize的含义。这篇文章涉及下列主题,并采用Hotspot JVM:

  • 垃圾回收器(Garbage Collector,GC)
  • 哪个JVM?
  • JVM命令行选项

垃圾回收器

垃圾回收器负责:

  • 分配内存
  • 保证所有正在被引用的对象还存在于内存中
  • 回收执行代码已经不再引用的对象所占的内存

应用执行时,定位和回收垃圾对象的过程会占用总执行时间的将近25%,这会拖累应用的执行效率。

Hotspot VM提供的垃圾回收器是一个分代垃圾回收器(Generational GC)[9,16,18]-将内存划分为不同的阶段,也就是说,不同的生命周期的对象放置在不同的地址池中。这样的设计是基于弱年代假设(Weak Generational Hypothesis):

1.越早分配的对象越容易失效;

2.老对象很少会引用新对象。

这种分代方式可以减少垃圾回收的停顿时间以及大范围对象的回收成本。Hotspot VM将其堆空间分为三个分代空间:

1. 年轻代Young Generation

○     Java应用在分配Java对象时,这些对象会被分配到年轻代堆空间中去

○     这个空间大多是小对象并且会被频繁回收

○     由于年轻代堆空间的垃圾回收会很频繁,因此其垃圾回收算法会更加重视回收效率

2. 年老代Old Generationn

○     年轻代堆空间的长期存活对象会转移到(也许是永久性转移)年老代堆空间

○     这个堆空间通常比年轻代的堆空间大,并且其空间增长速度较缓

○     由于大部分JVM堆空间都分配给了年老代,因此其垃圾回收算法需要更节省空间,此算法需要能够处理低垃圾密度的堆空间

3. 持久代Permanent Generation

○     存放VM和Java类的元数据(metadata),以及interned字符串和类的静态变量

次收集(Minor GC)和全收集(Full GC

当这三个分代的堆空间比较紧张或者没有足够的空间来为新到的请求分配的时候,垃圾回收机制就会起作用。有两种类型的垃圾回收方式:次收集和全收集。当年轻代堆空间满了的时候,会触发次收集将还存活的对象移到年老代堆空间。当年老代堆空间满了的时候,会触发一个覆盖全范围的对象堆的全收集。

次收集

  • 当年轻代堆空间紧张时会被触发
  • 相对于全收集而言,收集间隔较短

全收集

  • 当老年代或者持久代堆空间满了,会触发全收集操作
  • 可以使用System.gc()方法来显式的启动全收集
  • 全收集一般根据堆大小的不同,需要的时间不尽相同,但一般会比较长。不过,如果全收集时间超过3到5秒钟,那就太长了[1]

全收集通常时间最长,并且是程序无法延迟执行或者无法达到吞吐量目标的主因。GC的目标是去减少程序运行过程中垃圾回收的频率。为了达到这个目的,可以从这两方面入手:

  • 从系统方面考虑:

○    尽量采用大堆,但是不要大到需要系统从磁盘上“换”页。一般而言,可用的RAM(没有被系统进程占用的)的80%都应该分配给JVM。

○    Java堆空间越大,垃圾回收器和java应用在吞吐量(throughput)和延迟执行(latency)方面的效果越好。

  • 从应用方面考虑:

○    减少对象分配(object allocations)操作,或者采用对象保留(object retention)方式有助于减小存活的数据大小,这也可以反过来帮助垃圾回收做的更好。

○    参考这篇文章—Java性能提升窍门[19]

内存溢出错误(OutOfMemoryError

可怕的内存溢出错误是Java程序员最不愿意看到的。然而这个错误还是会出现,尤其应用中涉及到大量的数据处理时,或应用运行时间过长时。

一个应用所占内存大小包括:

  • Java堆大小
  • 线程栈
  • I/O缓冲区
  • 原生库所分配的内存

当一个应用耗尽了内存并且JVM GC也无法回收任何对象空间的时候,就会发生内存溢出错误。但是,内存溢出错误并不一定就意味着内存泄露(memory leak)。也有可能只是一个配置问题,例如设置的堆大小(如果没有设置那就是缺省的堆大小)对于应用来说是不够用的。

JVM命令行参数

无论是客户端应用还是服务器端应用,一旦系统运行缓慢并且垃圾回收所占时间过长,你就会希望通过调整堆大小来改善这一点。不过,为了不影响其他也跑在同一个系统中的应用,不应该将堆大小设置的过大。

GC调优是很重要的。找到最佳的分代堆空间是一个迭代的过程[3,10,12]。这里我们假定你已经为你的应用找到了最佳堆大小。那么你可以采用下面的JVM命令来进行设置:

GC 命令行选项 描述
-Xms 设置Java堆大小的初始值/最小值。例如:-Xms512m (请注意这里没有”=”).
-Xmx 设置Java堆大小的最大值
-Xmn 设置年轻代对空间的初始值,最小值和最大值。请注意,年老代堆空间大小是依赖于年轻代堆空间大小的
-XX:PermSize=<n>[g|m|k] 设置持久代堆空间的初始值和最小值
-XX:MaxPermSize=<n>[g|m|k] 设置持久代堆空间的最大值

最后一点,最早在Java SE 5.0中有对服务器的人机工程学的介绍[13]。这个可以很好的减少服务器端应用的调优时间,尤其是在堆大小测量和复杂GC调优方面。很多情况下,服务器端调优的最好方式就是不去调优。

参考文章

1         Tuning Java Virtual Machines (JVMs)

2        Diagnosing Java.lang.OutOfMemoryError

3        Java Performance by Charlie Hunt and Binu John

4        Java HotSpot VM Options

5        GCViewer (a free open source tool)

6        Comparison Between Sun JDK And Oracle JRockit

7        Java SE 6 Performance White Paper

8       F&Q about Garbage Collection

9        Hotspot Glossary of Terms

10    Memory Management in the Java HotSpot Virtual Machine White Paper

11     Java Hotspot Garbage Collection

12    FAQ about GC in the Hotspot JVM (with good details)

13    Java Heap Sizing: How do I size my Java heap correctly?

14    Java Tuning White Paper

15     JRockit JVM Heap Size Options

16    Pick up performance with generational garbage collection

17     Which JVM?

18    Memory Management in the Java HotSpot™ Virtual Machine

19    Java Performance Tips

英文原文: XML and more,翻译:ImportNew - 郑雯

译文地址: http://www.importnew.com/1551.html

《转载》JVM垃圾回收机制的更多相关文章

  1. [转载]JVM 垃圾回收机制(Garbage Collection)

    相关算法: 引用计数法 引用可达法 尚学堂 参考:http://www.sxt.cn/Java_jQuery_in_action/Principle_and_algorithm_of_garbage_ ...

  2. JVM垃圾回收机制总结:调优方法

    转载: JVM垃圾回收机制总结:调优方法 JVM 优化经验总结 JVM 垃圾回收器工作原理及使用实例介绍

  3. JVM内存管理和JVM垃圾回收机制

    JVM内存管理和JVM垃圾回收机制(1) 这里向大家描述一下JVM学习笔记之JVM内存管理和JVM垃圾回收的概念,JVM内存结构由堆.栈.本地方法栈.方法区等部分组成,另外JVM分别对新生代和旧生代采 ...

  4. JVM垃圾回收机制概述

    JVM垃圾回收机制概述 1.定义 是指JVM用于释放那些不再使用的对象所占用的内存. 2.方式 2.1引用计数(早期) 当引用程序创建引用以及引用超出范围时,JVM必须适当增减引用数.当某个对象的引用 ...

  5. Java虚拟机学习笔记——JVM垃圾回收机制

    Java虚拟机学习笔记——JVM垃圾回收机制 Java垃圾回收基于虚拟机的自动内存管理机制,我们不需要为每一个对象进行释放内存,不容易发生内存泄漏和内存溢出问题. 但是自动内存管理机制不是万能药,我们 ...

  6. JVM基础系列第8讲:JVM 垃圾回收机制

    在第 6 讲中我们说到 Java 虚拟机的内存结构,提到了这部分的规范其实是由<Java 虚拟机规范>指定的,每个 Java 虚拟机可能都有不同的实现.其实涉及到 Java 虚拟机的内存, ...

  7. JVM内存管理、JVM垃圾回收机制、新生代、老年代以及永久代

    内存模型 JVM运行时数据区由程序计数器.堆.虚拟机栈.本地方法栈.方法区部分组成,结构图如下所示. JVM内存结构由程序计数器.堆.栈.本地方法栈.方法区等部分组成,结构图如下所示: 1)程序计数器 ...

  8. JVM 垃圾回收机制和常见算法和 JVM 的内存结构和内存分配(面试题)

    一.JVM 垃圾回收机制和常见算法 Sun 公司只定义了垃圾回收机制规则而不局限于其实现算法,因此不同厂商生产的虚拟机采用的算法也不尽相同.GC(Garbage Collector)在回收对象前首先必 ...

  9. JVM垃圾回收机制和常用算法

    由于疫情的原因,所以目前一直在家远程办公,所以很多时间在刷面试题,发现2019大厂的面试虽然种类很多,但是总结了一下发现主要是这几点:算法和数据结构. JVM.集合.多线程.数据库这几点在面试的时候比 ...

  10. 真的可惜,四面阿里,结果我被JVM垃圾回收机制与 OOM异常卡住了

    前言 为什么需要垃圾回收 首先我们来聊聊为什么会需要垃圾回收,假设我们不进行垃圾回收会造成什么后果,我们举一个简单的例子 我们住在一个房子里面,我们每天都在里面生活,然后垃圾都丢在房子里面,又不打扫, ...

随机推荐

  1. db2 load报文件系统满

    使用db2 load导入数据 数据量比较大时常常会报文件系统已满错误. 原因分析:导入表建有索引,在load的“索引复制”阶段会从系统临时表空间拷贝到目标表空间,导致系统临时表空间所在的文件系统满,l ...

  2. 导出使用NPOI

    调用: DataTable table = new DataTable(); #region 创建 datatable table.Columns.Add(new DataColumn("账 ...

  3. HTML5 学习03——内联 SVG

    什么是SVG? SVG 指可伸缩矢量图形 (Scalable Vector Graphics) SVG 用于定义用于网络的基于矢量的图形 SVG 使用 XML 格式定义图形 SVG 图像在放大或改变尺 ...

  4. AndroidStudio中Handler类的内存溢出风险

    package com.test.king.xmlparser; import android.annotation.SuppressLint; import android.app.Activity ...

  5. [Pipy]利用pip2pi搭建本地pypi源

    当我们一个团队开发一个项目的时候,须要的Python第三方包基本是固定的.每次搭建新环境的时候总是由于各种内外网,https问题花费大量的时间来安装执行环境. 所以搭建一个本地的,小巧的,仅仅包括须要 ...

  6. python接口自动化测试(一)-环境准备

    接口测试的方式有很多,比如可以用工具(jmeter,postman)之类,也可以自己写代码进行接口测试,工具的使用相对来说都比较简单,重点是要搞清楚项目接口的协议是什么,然后有针对性的进行选择,甚至当 ...

  7. 关于4A(统一安全管理平台)系统的理解

    1. 4A系统的需求分析 近年来企业用户的业务系统发展十分迅速,内部的系统数和用户数不断增加,网络规模迅速扩大,在应用扩展的同时,各业务系统的安全管理工作相对滞后,无法满足企业发展的长期要求. 各系统 ...

  8. masonry 基本用法

    一:masonry 基本用法 fistView=[[UIView alloc] init]; fistView.backgroundColor=[UIColor redColor]; [self.vi ...

  9. CAShapeLayer(UIBezierPath)、CAGradientLayer绘制动态小车

    看到一个大神写的代码,引用过来让大家看看! //  1.CAShapeLayer是一种特殊的层,可以在上面渲染图形. //  2.CAShapeLayer继承自CALayer,可使用CALayer的所 ...

  10. Unity应用架构设计(1)—— MVVM 模式的设计和实施(Part 1)

    初识 MVVM 谈起 MVVM 设计模式,可能第一映像你会想到 WPF/Sliverlight,他们提供了的数据绑定(Data Binding),命令(Command)等功能,这让 MVVM 模式得到 ...