`
langgufu
  • 浏览: 2289498 次
  • 性别: Icon_minigender_1
  • 来自: 北京
社区版块
存档分类
最新评论

Java堆内存的10个要点

阅读更多

 当我开始学习 Java 编程时,我不知道什么是堆内存或堆空间,我甚至不知道当对象创建时,它们被放在了哪里。当我开始正式写一些程序后,我会经常遇到 java.lang.outOfMemoryError 的报错,之后我才开始关注什么是堆内存或者说堆空间(heap space)。对大多数程序员都经历过这样的过程,因为学习一种语言是非常容易来的,但是学习基础是非常难的,因为没有什么特定的流程让你学习编程的每个基础,使你发觉编程的秘诀。对于程序员来说,知道堆空间,设置堆空间,处理堆空间的 outOfMemoryError 错误,分析 heap dump 是非常重要的。这个关于 Java 堆的教程是给我刚开始学编程的兄弟看的。如果你知道这个基础知识或者知道底层发生了什么,当然可能帮助不是那么大。除非你知道了对象被创建在堆中,否则你不会意识到 OutOfMemoryError 是发生在堆空间中的。我尽可能的将我所知道的所有关于堆的知识都写下来了,也希望你们能够尽可能多的贡献和分享你的知识,以便可以让其他人也受益。

  Java 中的堆空间是什么?

  当 Java 程序开始运行时,JVM 会从操作系统获取一些内存。JVM 使用这些内存,这些内存的一部分就是堆内存。堆内存通常在存储地址的底层,向上排列。当一个对象通过 new 关键字或通过其他方式创建后,对象从堆中获得内存。当对象不再使用了,被当做垃圾回收掉后,这些内存又重新回到堆内存中。要学习垃圾回收,请阅读”Java 中垃圾回收的工作原理”。

  如何增加 Java 堆空间

  在大多数 32 位机、Sun 的 JVM 上,Java 的堆空间默认的大小为 128MB,但也有例外,例如在 32 未 Solaris 操作系统(SPARC 平台版本)上,默认的最大堆空间和起始堆空间大小为 -Xms=3670K 和 -Xmx=64M。对于 64 位操作系统,一般堆空间大小增加约 30%。但你使用 Java 1.5 的 throughput 垃圾回收器,默认最大的堆大小为物理内存的四分之一,而起始堆大小为物理内存的十六分之一。要想知道默认的堆大小的方法,可以用默认的设置参数打开一个程序,使用 JConsole (JDK 1.5 之后都支持)来查看,在 VM Summary 页面可以看到最大的堆大小。

  用这种方法你可以根据你的程序的需要来改变堆内存大小,我强烈建议采用这种方法而不是默认值。如果你的程序很大,有很多对象需要被创建的话,你可以用-Xms and -Xmx 这两个参数来改变堆内存的大小。Xms 表示起始的堆内存大小,Xmx 表示最大的堆内存的大小。另外有一个参数 -Xmn,它表示 new generation(后面会提到)的大小。有一件事你需要注意,你不能任意改变堆内存的大小,你只能在启动 JVM 时设定它。

  堆和垃圾回收

  我们知道对象创建在堆内存中,垃圾回收这样一个进程,它将已死对象清除出堆空间,并将这些内存再还给堆。为了给垃圾回收器使用,堆主要分成三个区域,分别叫作 New Generation,Old Generation 或叫 Tenured Generation,以及 Perm space。New Generation 是用来存放新建的对象的空间,在对象新建的时候被使用。如果长时间还使用的话,它们会被垃圾回收器移动到 Old Generation (或叫 Tenured Generation)。Perm space 是 JVM 存放 Meta 数据的地方,例如类,方法,字符串池和类级别的详细信息。你可以查看“Java 中垃圾回收的工作原理”来获得更多关于堆和垃圾回收的信息。

java

  Java 堆中的 OutOfMemoryError 错误

  当 JVM 启动时,使用了-Xms 参数设置的对内存。当程序继续进行,创建更多对象,JVM 开始扩大堆内存以容纳更多对象。JVM 也会使用垃圾回收器来回收内存。当快达到-Xmx 设置的最大堆内存时,如果没有更多的内存可被分配给新对象的话,JVM 就会抛出 java.lang.outofmemoryerror,你的程序就会当掉。在抛出 OutOfMemoryError 之前,JVM 会尝试着用垃圾回收器来释放足够的空间,但是发现仍旧没有足够的空间时,就会抛出这个错误。为了解决这个问题,你需要清楚你的程序对象的信息,例如,你创建了哪些对象,哪些对象占用了多少空间等等。你可以使用 profiler 或者堆分析器来处理 OutOfMemoryError 错误。”java.lang.OutOfMemoryError: Java heap space”表示堆没有足够的空间了,不能继续扩大了。”java.lang.OutOfMemoryError: PermGen space”表示 permanent generation 已经装满了,你的程序不能再装在类或者再分配一个字符串了。

  Java Heap dump

  Heap dump 是在某一时间对 Java 堆内存的快照。它对于分析堆内存或处理内存泄露和 Java.lang.outofmemoryerror 错误是非常有用的。在 JDK 中有一些工具可以帮你获取 heap dump,也有一些堆分析工具来帮你分析 heap dump。你可以用“jmap”来获取 heap dump,它帮你创建 heap dump 文件,然后,你可以用“jhat”(堆分析工具)来分析这些 heap dump。

  Java 堆内存(heap memory)的十个要点

  1. Java 堆内存是操作系统分配给 JVM 的内存的一部分。

  2. 当我们创建对象时,它们存储在 Java 堆内存中。

  3. 为了便于垃圾回收,Java 堆空间分成三个区域,分别叫作 New Generation, Old Generation 或叫作 Tenured Generation,还有 Perm Space。

  4. 你可以通过用 JVM 的命令行选项 -Xms, -Xmx, -Xmn 来调整 Java 堆空间的大小。不要忘了在大小后面加上”M”或者”G”来表示单位。举个例子,你可以用 -Xmx256m 来设置堆内存最大的大小为 256MB。

  5. 你可以用 JConsole 或者 Runtime.maxMemory (), Runtime.totalMemory (), Runtime.freeMemory ()来查看 Java 中堆内存的大小。

  6. 你可以使用命令“jmap”来获得 heap dump,用“jhat”来分析 heap dump。

  7. Java 堆空间不同于栈空间,栈空间是用来储存调用栈和局部变量的。

  8. Java 垃圾回收器是用来将死掉的对象(不再使用的对象)所占用的内存回收回来,再释放到 Java 堆空间中。

  9. 当你遇到 java.lang.outOfMemoryError 时,不要紧张,有时候仅仅增加堆空间就可以了,但如果经常出现的话,就要看看 Java 程序中是不是存在内存泄露了。

  10. 请使用 Profiler 和 Heap dump 分析工具来查看 Java 堆空间,可以查看给每个对象分配了多少内存。

分享到:
评论

相关推荐

    基于Java堆内存的10个要点的总结分析

    本篇文章是对Java堆内存的10个要点进行了详细的分析介绍,需要的朋友参考下

    Java虚拟机监控方案.docx

     通过虚拟机内置的jstat指令获取内存各种堆和非堆的大小及其内存使用量  通过虚拟机内置jstack获取虚拟机线程的执行堆栈  统计、分析之后的数据封装为用于被监控数据对象,向各种渠道的数据观察者发送监控数据...

    C++内存管理.doc

    因此要想成为C++高手,内存管理一关是必须要过的,除非放弃C++,转到Java或者.NET,他们的内存管理基本是自动的,当然你也放弃了自由和对内存的支配权,还放弃了C++超绝的性能。本期专题将从内存管理、内存泄漏、...

    leetcode分类-OfferMe2020:整理计算机专业复习要点、面试题、以及牛客和LeetCode上在线编程题

    出来的,位于堆内存。每个成员变量在不同对象中都有不同的值(除了静态变量),而方法只有一份,执行的时候才占用内存。 static 静态变量、常量,位于数据区(Data Segment) 为了管理大型软件系统中数目众多的类,...

    程序员面试攻略 part1(共2个)

    独辟蹊径,角度很好,尤其适合我们要找一个好工作的想法,你为公司做了很多事情,也学了很多技术,可是 面试的题目你不一定能够过关,因为面试考题角度特别。要提高自己的生存能力,还是多研究一下吧。我看了前面的...

    程序员面试攻略part 2(共2个)

    独辟蹊径,角度很好,尤其适合我们要找一个好工作的想法,你为公司做了很多事情,也学了很多技术,可是 面试的题目你不一定能够过关,因为面试考题角度特别。要提高自己的生存能力,还是多研究一下吧。我看了前面的...

    leetcode分类--:BN理解

    java的原理 比如C++多态如何实现 static的用法 内存分区 STL库的底层实现 数据结构问排序 红黑树 平衡二叉树 二叉堆哈希之类的原理 有时候会问相关算法 操作系统偏向于进程线程部分 死锁部分和内存部分 计算机网络会...

    Spring面试题

    没有使用一堆抽象工厂、服务定位器、单元素(singleton)和直接构造(straight construction),每一个对象都是用其协作对象构造的。因此是由容器管理协作对象(collaborator)。 Spring即使一个AOP框架,也是一IOC...

    C++大学教程,一本适合初学者的入门教材(part1)

    1.9 Java、Internet与万维网 1.10 其他高级语言 1.11 结构化编程 1.12 典型C++环境基础 1.13 C++与本书的一般说明 1.14 C++编程简介 1.15 简单程序:打印一行文本 1.16 简单程序:两个整数相加 1.17 内存的...

    SQLServer2008查询性能优化 2/2

    《SQL Server 2008查询性能优化》指出的性能要点之一是数据库随着用户和数据的日益增多而进行扩展的必要性。你需要理解性能低下的起因。以及识别并修复它们的方法。《SQL Server 2008查询性能优化》将帮助你: 使用...

    SQLServer2008查询性能优化 1/2

    《SQL Server 2008查询性能优化》指出的性能要点之一是数据库随着用户和数据的日益增多而进行扩展的必要性。你需要理解性能低下的起因。以及识别并修复它们的方法。《SQL Server 2008查询性能优化》将帮助你: 使用...

    Visual C++ 2005入门经典--源代码及课后练习答案

    Ivor Horton还著有Beginning Visual C++ 6、Beginning C Programming和Beginning Java 2等多部入门级好书。 目录 封面 -18 前言 -14 目录 -9 第1章 使用Visual C++ 2005编程 1 1.1 .NET Framework 1 1.2 CLR 2...

    C++大学教程,一本适合初学者的入门教材(part2)

    1.9 Java、Internet与万维网 1.10 其他高级语言 1.11 结构化编程 1.12 典型C++环境基础 1.13 C++与本书的一般说明 1.14 C++编程简介 1.15 简单程序:打印一行文本 1.16 简单程序:两个整数相加 1.17 内存的...

    Visual C++ 2010入门经典(第5版)--源代码及课后练习答案

     Ivor Horton是撰著Java、C和C++编程语言图书的杰出作家之一。大家一致认为,他的著作独具风格,无论是编程新手,还是经验丰富的编程人员,都很容易理解其内容。在个人实践中,Ivor Horton也是一名系统顾问。他从事...

Global site tag (gtag.js) - Google Analytics