从 Java 代码到 Java 堆
理解和优化您的应用程序的内存使用
https://www.ibm.com/developerworks/cn/java/j-codetoheap/
优化应用程序代码的内存使用并不是一个新主题,但是人们通常并没有很好地理解这个主题。本文将简要介绍 Java 进程的内存使用,随后深入探讨您编写的 Java 代码的内存使用。最后,本文将展示提高代码内存效率的方法,特别强调了 HashMap
和 ArrayList
等 Java 集合的使用。
背景信息:Java 进程的内存使用
通过在命令行中执行 java
或者启动某种基于 Java 的中间件来运行 Java 应用程序时,Java
运行时会创建一个操作系统进程,就像您运行基于 C 的程序时那样。实际上,大多数 JVM 都是用 C 或者 C++
语言编写的。作为操作系统进程,Java 运行时面临着与其他进程完全相同的内存限制:架构提供的寻址能力以及操作系统提供的用户空间。
架构提供的内存寻址能力依赖于处理器的位数,举例来说,32 位或者 64 位,对于大型机来说,还有 31
位。进程能够处理的位数决定了处理器能寻址的内存范围:32 位提供了 2^32 的可寻址范围,也就是 4,294,967,296 位,或者说
4GB。而 64 位处理器的可寻址范围明显增大:2^64,也就是 18,446,744,073,709,551,616,或者说 16
exabyte(百亿亿字节)。
处理器架构提供的部分可寻址范围由 OS 本身占用,提供给操作系统内核以及 C 运行时(对于使用 C 或者 C++ 编写的 JVM
而言)。OS 和 C 运行时占用的内存数量取决于所用的 OS,但通常数量较大:Windows 默认占用的内存是
2GB。剩余的可寻址空间(用术语来表示就是用户空间
)就是可供运行的实际进程使用的内存。
对于 Java 应用程序,用户空间是 Java 进程占用的内存,实际上包含两个池:Java 堆和本机
(非 Java)堆。Java 堆的大小由 JVM 的 Java 堆设置控制:-Xms
和 -Xmx
分别设置最小和最大 Java 堆。在按照最大的大小设置分配了 Java 堆之后,剩下的用户空间就是本机堆。图 1 展示了一个 32 位 Java 进程的内存布局:
图 1. 一个 32 位 Java 进程的内存布局示例
在 图 1
中,可寻址范围总共有 4GB,OS 和 C 运行时大约占用了其中的 1GB,Java 堆占用了将近 2GB,本机堆占用了其他部分。请注意,JVM 本身也要占用内存,就像 OS 内核和 C 运行时一样,而 JVM 占用的内存是本机堆的子集。
回页首
Java 对象详解
在您的 Java 代码使用 new
操作符创建一个 Java 对象的实例时,实际上分配的数据要比您想的多得多。例如,一个 int
值与一个 Integer
对象(能包含 int
值的最小对象)的大小比率是 1:4,这个比率可能会让您感到吃惊。额外的开销源于 JVM 用于描述 Java 对象的元数据,在本例中也就是 Integer
。
根据 JVM 的版本和供应的不同,对象元数据的数量也各有不同,但其中通常包括:
-
类
:一个指向类信息的指针,描述了对象类型。举例来说,对于
java.lang.Integer
对象,这是 java.lang.Integer
类的一个指针。
-
标记
:一组标记,描述了对象的状态,包括对象的散列码(如果有),以及对象的形状
(也就是说,对象是否是数组)。
-
锁
:对象的同步信息,也就是说,对象目前是否正在同步。
对象元数据后紧跟着对象数据本身,包括对象实例中存储的字段。对于 java.lang.Integer
对象,这就是一个 int
。
如果您正在运行一个 32 位 JVM,那么在创建 java.lang.Integer
对象实例时,对象的布局可能如图 2 所示:
图 2. 一个 32 位 Java 进程的 java.lang.Integer
对象的布局示例
如 图 2
所示,有 128 位的数据被占用,其中用于存储 int
值的为 32 位,而对象元数据占用了其余的 96 位。
相关推荐
【描述】:本文旨在帮助Java开发者深入了解从编写代码到Java堆的内存管理过程,以便更好地优化应用程序的内存使用。通过分析Java代码中的内存开销,以及讨论对象创建、集合效率等方面,将揭示如何确定性能瓶颈并改进...
首先,Java代码的内存使用量的理解,是从基本的数据类型和对应的包装类对象存储差异开始的。例如,基本类型`int`和对应的包装类`Integer`在内存使用上有明显的不同。`int`是4字节固定大小,而`Integer`对象却需要更...
Java代码优化是提升应用程序性能的关键步骤,尤其是在大型企业级应用或者高性能服务中。优化能够减少内存消耗,提高程序运行速度,降低CPU使用率,并改善整体的用户体验。在Java开发领域,有多种工具可以帮助开发者...
总的来说,“Java程序性能优化 让你的Java程序更快、更稳定”这本书将涵盖以上诸多方面,通过理论结合实际的示例代码,帮助读者深入理解Java性能优化的各个方面,从而写出更快、更稳定的Java程序。书中附带的源文件...
### 优化Java堆大小的五个技巧详解 #### 一、JVM:理解基本原理与内存管理 ##### **1.1 JVM内存模型** ...在实践中,开发者应当结合具体的项目需求和技术背景,灵活运用这些技巧来优化应用的内存使用。
有一些第三方库,如JavaMelody和VisualVM Lite,可以帮助开发者集成到应用程序中,提供实时的内存使用报告。这些库通常提供丰富的图表和报警机制,使得内存管理更加直观和高效。 6. **内存泄漏检测** 除了实时...
理解堆内存的划分、分配机制和垃圾回收过程对于Java开发者来说至关重要,因为这些知识可以帮助他们优化应用程序的性能,避免内存泄漏和溢出问题。本文将详细介绍Java堆内存的划分、内存分配策略以及垃圾回收机制,并...
由于这些特性,堆内存的管理较为复杂,但同时也为Java应用程序提供了极大的灵活性。 - **特点**: - 动态分配:对象的大小不固定。 - 生命周期不确定:对象可能在任意时间被垃圾回收。 - 灵活性高:可以自由创建...
除了Java堆内存之外,Java应用程序还需要使用到**本机内存**(Native Memory),这是指JVM之外的内存,主要用于存储JVM自身的元数据、线程栈以及一些非Java对象的数据结构。 - **元数据**:包括类定义、字段信息、...
本文将深入探讨Java代码优化的相关知识点,结合提供的书籍资源——《代码大全-第二版》、《重构-改善既有代码的设计(简体中文)》以及《Java设计模式中文版》,我们将从多个角度来讨论如何提升Java代码的质量和效率。...
1. **JVM内存模型**:理解堆内存、栈内存、方法区以及垃圾回收机制,如何调整JVM参数以优化内存分配,避免内存泄漏和频繁的垃圾回收。 2. **代码优化**:编写高效代码,避免冗余计算,合理使用循环和条件判断,以及...
Java程序性能优化是每个开发人员都需要关注的重要领域,它涵盖了多个方面,旨在提高代码执行效率,减少资源消耗,以及提升应用程序的稳定性和响应速度。在本文中,我们将深入探讨Java性能优化的关键点,帮助你的Java...
通过阅读代码,我们可以学习到如何使用Java API与安卓系统交互,如何实现系统优化算法,以及如何设计高效的垃圾清理策略。同时,这也为我们提供了自我实践和二次开发的机会,可以根据自己的需求对软件进行定制和改进...
在Java开发中,程序性能优化是一个重要的环节,它直接影响到应用程序的运行效率、用户体验以及系统的整体稳定性。本文将基于提供的标题、描述及部分内容,深入探讨几个关键性的性能优化策略。 #### 一、理解Java...
Java程序性能优化是Java开发中的重要环节,它旨在提高应用程序的运行效率,减少资源消耗,提升用户体验。在Java世界中,性能优化涵盖了多个层面,包括代码优化、内存管理、线程调度、数据库交互以及JVM参数调整等。...
Java优化编程是提升Java应用程序性能的关键技术,涵盖了多个方面的知识,包括代码优化、内存管理、垃圾回收、并发处理以及JVM参数调优等。以下是对这些主题的详细讲解: 1. **代码优化**:编写高效的Java代码是优化...
5. **MVC(Model-View-Controller)设计模式**:在Java Web开发中,MVC模式被广泛应用于组织应用程序结构。了解模型、视图和控制器各自的角色,以及它们之间的交互,有助于构建清晰的项目架构。 6. **Struts框架**...
《代码优化:有效使用内存》是一本专注于提升软件性能的关键技术书籍,主要针对应用程序员和系统程序员,旨在帮助他们编写更高效、占用内存更少的代码。这本书不仅对程序员有极大的学习价值,对于硬件领域的专业人士...
《Java代码与架构之完美优化——实战经典》是一本深入探讨Java编程语言和架构优化的书籍,其配套代码集提供了一系列实例,旨在帮助读者更好地理解并应用书中的理论知识。这个压缩包包含的文件名为“03_《Java代码与...
通过研究和实践这些JavaME源程序代码,开发者可以掌握如何在资源有限的设备上进行高效编程,了解如何利用JavaME的特性创建跨平台的应用程序。同时,这对于理解移动设备的性能限制、优化代码以及调试技巧也是非常有...