`

java虚拟机内存管理机制(一):JVM内存管理总结【分享】

    博客分类:
  • jvm
阅读更多

近期看了看Java内存泄露的一些案例,跟原来的几个哥们讨论了一下,深入研究发现JVM里面还是有不少以前不知道的细节,这里稍微剖析一下。先看一看JVM的内部结构——


如图所示,JVM主要包括两个子系统和两个组件。两个子系统分别是Class loader子系统和Execution engine(执行引擎) 子系统;两个组件分别是Runtime data area (运行时数据区域)组件和Native interface(本地接口)组件。
 
Class loader子系统的作用:根据给定的全限定名类名(如 java.lang.Object)来装载class文件的内容到 Runtime data area中的method area(方法区域)。Java程序员可以extends java.lang.ClassLoader类来写自己的Class loader。  

Execution engine子系统的作用:执行classes中的指令。任何JVM specification实现(JDK)的核心都是Execution engine,不同的JDK例如Sun 的JDK 和IBM的JDK好坏主要就取决于他们各自实现的Execution engine的好坏。

Native interface组件:与native libraries交互,是其它编程语言交互的接口。当调用native方法的时候,就进入了一个全新的并且不再受虚拟机限制的世界,所以也很容易出现JVM无法控制的native heap OutOfMemory。

Runtime Data Area组件:这就是我们常说的JVM的内存了。它主要分为五个部分——
1、Heap (堆):一个Java虚拟实例中只存在一个堆空间
2、Method Area(方法区域):被装载的class的信息存储在Method area的内存中。当虚拟机装载某个类型时,它使用类装载器定位相应的class文件,然后读入这个class文件内容并把它传输到虚拟机中。
3、Java Stack(java的栈):虚拟机只会直接对Java stack执行两种操作:以帧为单位的压栈或出栈
4、Program Counter(程序计数器):每一个线程都有它自己的PC寄存器,也是该线程启动时创建的。PC寄存器的内容总是指向下一条将被执行指令的饿地址,这里的地址可以是一个本地指针,也可以是在方法区中相对应于该方法起始指令的偏移量。  
5、Native method stack(本地方法栈):保存native方法进入区域的地址

以上五部分只有Heap 和Method Area是被所有线程的共享使用的;而Java stack, Program counter 和Native method stack是以线程为粒度的,每个线程独自拥有自己的部分。

了解JVM的系统结构,再来看看JVM内存回收问题了——
Sun的JVM Generational Collecting(垃圾回收)原理是这样的:把对象分为年青代(Young)、年老代(Tenured)、持久代(Perm),对不同生命周期的对象使用不同的算法。(基于对对象生命周期分析)


如上图所示,为Java堆中的各代分布。  
1. Young(年轻代)
年轻代分三个区。一个Eden区,两个Survivor区。大部分对象在Eden区中生成。当Eden区满时,还存活的对象将被复制到Survivor区(两个中的一个),当这个Survivor区满时,此区的存活对象将被复制到另外一个Survivor区,当这个Survivor去也满了的时候,从第一个Survivor区复制过来的并且此时还存活的对象,将被复制年老区(Tenured。需要注意,Survivor的两个区是对称的,没先后关系,所以同一个区中可能同时存在从Eden复制过来 对象,和从前一个Survivor复制过来的对象,而复制到年老区的只有从第一个Survivor去过来的对象。而且,Survivor区总有一个是空的。  
2. Tenured(年老代)
年老代存放从年轻代存活的对象。一般来说年老代存放的都是生命期较长的对象。  
3. Perm(持久代)
用于存放静态文件,如今Java类、方法等。持久代对垃圾回收没有显著影响,但是有些应用可能动态生成或者调用一些class,例如Hibernate等,在这种时候需要设置一个比较大的持久代空间来存放这些运行过程中新增的类。持久代大小通过-XX:MaxPermSize=进行设置。

举个例子:当在程序中生成对象时,正常对象会在年轻代中分配空间,如果是过大的对象也可能会直接在年老代生成(据观测在运行某程序时候每次会生成一个十兆的空间用收发消息,这部分内存就会直接在年老代分配)。年轻代在空间被分配完的时候就会发起内存回收,大部分内存会被回收,一部分幸存的内存会被拷贝至Survivor的from区,经过多次回收以后如果from区内存也分配完毕,就会也发生内存回收然后将剩余的对象拷贝至to区。等到to区也满的时候,就会再次发生内存回收然后把幸存的对象拷贝至年老区。

通常我们说的JVM内存回收总是在指堆内存回收,确实只有堆中的内容是动态申请分配的,所以以上对象的年轻代和年老代都是指的JVM的Heap空间,而持久代则是之前提到的Method Area,不属于Heap。

了解完这些之后,以下的转载一热衷于钻研技术的哥们Richen Wang关于内存管理的一些建议——
1、手动将生成的无用对象,中间对象置为null,加快内存回收。
2、对象池技术 如果生成的对象是可重用的对象,只是其中的属性不同时,可以考虑采用对象池来较少对象的生成。如果有空闲的对象就从对象池中取出使用,没有再生成新的对象,大大提高了对象的复用率。
3、JVM调优 通过配置JVM的参数来提高垃圾回收的速度,如果在没有出现内存泄露且上面两种办法都不能保证内存的回收时,可以考虑采用JVM调优的方式来解决,不过一定要经过实体机的长期测试,因为不同的参数可能引起不同的效果。如-Xnoclassgc参数等。

推荐的两款内存检测工具
1、jconsole JDK自带的内存监测工具,路径jdk bin目录下jconsole.exe,双击可运行。连接方式有两种,第一种是本地方式如调试时运行的进程可以直接连,第二种是远程方式,可以连接以服务形式启动的进程。远程连接方式是:在目标进程的jvm启动参数中添加-Dcom.sun.management.jmxremote.port=1090 -Dcom.sun.management.jmxremote.ssl=false -Dcom.sun.management.jmxremote.authenticate=false 1090是监听的端口号具体使用时要进行修改,然后使用IP加端口号连接即可。通过该工具可以监测到当时内存的大小,CPU的使用量以及类的加载,还提供了手动gc的功能。优点是效率高,速度快,在不影响进行运行的情况下监测产品的运行。缺点是无法看到类或者对象之类的具体信息。使用方式很简单点击几下就可以知道功能如何了,确实有不明白之处可以上网查询文档。

2、JProfiler 收费的工具,但是到处都有破解办法。安装好以后按照配置调试的方式配置好一个本地的session即可运行。可以监测当时的内存、CPU、线程等,能具体的列出内存的占用情况,还可以就某个类进行分析。优点很多,缺点太影响速度,而且有的类可能无法被织入方法,例如我使用jprofiler时一直没有备份成功过,总会有一些类的错误

 

 

简单的概念:

 

  • 堆(Heap)和非堆(Non-heap)内存
    按照官方的说法:“Java 虚拟机具有一个堆,堆是运行时数据区域,所有类实例和数组的内存均从此处分配。堆是在 Java 虚拟机启动时创建的。”“在JVM中堆之外的内存称为非堆内存(Non-heap memory)”。可以看出JVM主要管理两种类型的内存:堆和非堆。简单来说堆就是Java代码可及的内存,是留给开发人员使用的;非堆就是JVM留给 自己用的,所以方法区、JVM内部处理或优化所需的内存(如JIT编译后的代码缓存)、每个类结构(如运行时常数池、字段和方法数据)以及方法和构造方法 的代码都在非堆内存中。

 

  • 堆内存分配
    JVM初始分配的内存由-Xms指定,默认是物理内存的1/64;JVM最大分配的内存由 -Xmx指定,默认是物理内存的1/4。默认空余堆内存小于40%时,JVM就会增大堆直到-Xmx的最大限制;空余堆内存大于70%时,JVM会减少堆 直到-Xms的最小限制。因此服务器一般设置-Xms、-Xmx相等以避免在每次GC 后调整堆的大小。

 

  • 非堆内存分配
    JVM使用-XX:PermSize设置非堆内存初始值,默认是物理内存的1/64;由XX:MaxPermSize设置最大非堆内存的大小,默认是物理内存的1/4。

 

  • JVM内存限制(最大值)
    首先JVM内存限制于实际的最大物理内存(废话!呵呵),假设物理内存无限 大的话,JVM内存的最大值跟操作系统有很大的关系。简单的说就32位处理器虽然可控内存空间有4GB,但是具体的操作系统会给一个限制,这个限制一般是 2GB-3GB(一般来说Windows系统下为1.5G-2G,Linux系统下为2G-3G),而64bit以上的处理器就不会有限制了

 

分享到:
评论

相关推荐

    深入Java虚拟机(原书第2版).pdf【附光盘内容】

    《深入Java虚拟机(原书第2版)》,原书名《Inside the Java Virtual Machine,Second Edition》,作者:【美】Bill Venners,翻译:曹晓钢、蒋靖,出版社:机械工业出版社,ISBN:7111128052,出版日期:2003 年 9 ...

    Java内存管理机制相关资料汇总

    资源名称:Java内存管理机制相关资料汇总资源目录:【】java内存回收机制及预防【】java内存管理机制【】java内存管理白皮书【】Java虚拟机内存管理_对象和引用_空指针【】深入理解java虚拟机jvm高级行与最佳实践...

    java虚拟机2021面试题第一季

    JVM (Java Virtual Machine) 是Java平台的核心组件之一,它是一个虚拟机,用于在计算机上执行Java字节码。 JVM的主要功能有以下几个: 1. Java字节码执行:JVM能够解释和执行Java字节码。Java代码在编译后生成字节...

    java虚拟机2021面试题第二季

    JVM (Java Virtual Machine) 是Java平台的核心组件之一,它是一个虚拟机,用于在计算机上执行Java字节码。 JVM的主要功能有以下几个: 1. Java字节码执行:JVM能够解释和执行Java字节码。Java代码在编译后生成字节...

    java虚拟机2021面试题第三季

    JVM (Java Virtual Machine) 是Java平台的核心组件之一,它是一个虚拟机,用于在计算机上执行Java字节码。 JVM的主要功能有以下几个: 1. Java字节码执行:JVM能够解释和执行Java字节码。Java代码在编译后生成字节...

    Java知识,JVM面试资料

    JVM(Java虚拟机)是Java平台的核心组件之一,它是一个在计算机上运行Java字节码的虚拟机。JVM 提供了Java程序运行的环境和基础设施,并且具有高度的可移植性和跨平台性。 JVM 的主要功能包括字节码解释和执行、...

    最新java面试专题01-JVM

    JVM内存结构:JVM的内存结构主要包括堆内存、方法区、栈(包括Java虚拟机栈和本地方法栈)、程序计数器等。堆内存是所有线程共享的内存区域,用于存放对象实例;方法区保存已加载的类信息、常量、静态变量和编译后的...

    JAVA虚拟机全面理解.docx

    其中基础结构层包括Java虚拟机的所有基本功能,如内存管理、线程管理、类加载机制等;执行引擎层则负责解释Java字节码并执行;应用层则提供了与具体应用相关的功能,如安全管理器、垃圾收集器等。

    java虚拟机知识点整理

    自己看书整理的 java虚拟机精品知识点 java内存区域与内存溢出处理 虚拟机栈和本地方法栈区别 对象定位访问 垃圾收集器GC管理 虚拟机GC垃圾回收收集算法(内存回收方法论) 虚拟机GC垃圾回收收集器(内存回收具体实现...

    深入理解Java虚拟机精华知识点

    Java虚拟机(JVM)是Java Virtual Machine的缩写,它是一种规范用于计算设备。引入Java虚拟机后,Java语言在不同平台上运行时不需要重新编译。Java语言编译程序只需生成在Java虚拟机上运行的目标代码(字节码),就...

    JVM自动内存管理机制

    Java自动内存管理机制包含两部分:内存分配和内存回收,要想理解内存分配和回收的机制,则需要了解下Java内存区域(Java运行时数据区),这篇随笔将按照下面的线索进行逐步解析:1.Java运行时数据区2.对象“已死”的...

    详细讲解了jvm在java中应用

    JVM:全称 Java Virtual Machine,一个虚拟计算机,Java 程序的运行环境(Java二进制字节码的运行环境) 特点:Java 虚拟机基于二进制字节码执行,由一套字节码指令集、一组寄存器、一个栈、一个垃圾回收堆、一个...

    深入理解_Java_虚拟机 JVM_高级特性与最佳实践

    / 13 1.5 实战:自己编译JDK / 13 1.5.1 获取JDK源码 / 13 1.5.2 系统需求 / 14 1.5.3 构建编译环境 / 15 1.5.4 准备依赖项 / 17 1.5.5 进行编译 / 18 1.6 本章小结 / 21 第二部分 自动内存管理机制 ...

    jvm详解(java虚拟机详解)

    jvm详解高清pdf版,本文详细讲解了 JVM(Java Virtual Machine)的方方面面,首先由 java 的特性来描绘 JVM 的大致应用,再细细阐述了 JVM 的原理及内存管理机制和调优.最后讲述了与 JVM 密切相 关的 Java GC 机制.

    Java八股文的面试题

    Java虚拟机(JVM): JVM是运行所有Java程序的虚拟机环境,实现了Java的跨平台特性。JVM负责将Java字节码转换为机器码执行,同时提供内存管理和垃圾回收等功能。 垃圾回收(GC): Java通过垃圾回收机制自动管理内存,...

    Java虚拟机

    第二部分 自动内存管理机制 第2章 Java内存区域与内存溢出异常 2.1 概述 2.2 运行时数据区域 2.2.1 程序计数器 2.2.2 Java虚拟机栈 2.2.3 本地方法栈 2.2.4 Java堆 2.2.5 方法区 2.2.6 运行时常量池 2.2.7...

    JVM内存管理白皮书

    sun公司出版的jvm运行机制管理丛书,需要深入jvm的同学可以下载来看看

    Java面试整理,涵盖基础、JVM、线程并发、框架、MySQL、微服务、Redis、中间件、数据结构与算法等。陆续完善中.zip

    Java是一种高性能、跨平台的面向...自动内存管理(垃圾回收): Java具有自动内存管理机制,通过垃圾回收器自动回收不再使用的对象,使得开发者不需要手动管理内存,减轻了程序员的负担,同时也减少了内存泄漏的风险。

    学习Java基本语法的仓库 存放学习Java的md文件和Java代码.rar

    java虚拟机 jvm java virtual machine 1. jvm是一个虚拟的计算机,具有指令集并使用不同的存储区域。负责执行管理数据、内存、寄存器,包含在JDK中 2. 不同平台,不同虚拟机 3. java虚拟机屏蔽了底层运行平台的...

    高级java笔试题-understanding-the-jvm:《深入理解Java虚拟机》阅读笔记

    内存管理机制和 Java 虚拟机程序执行需要重点掌握,并且内容也是比较多的。本 repo 将原书中有关虚拟机性能监控及故障处理的部分单抽了出来,组成了本 repo 的第三部分。第四部分对应于原书的第四部分,程序编译与...

Global site tag (gtag.js) - Google Analytics