Java 内存溢出(二)使用 MAT 分析 .hprof 内存映像文件

这篇具有很好参考价值的文章主要介绍了Java 内存溢出(二)使用 MAT 分析 .hprof 内存映像文件。希望对大家有所帮助。如果存在错误或未考虑完全的地方,请大家不吝赐教,您也可以点击"举报违法"按钮提交疑问。

.hprof 文件: 是 java 项目的 Heap Dump 文件,也叫内存映像文件、内存快照文件,可以存放一个 java 进程在某个时间点的内存快照。生成 Heap Dump 文件的方式有两种:一是使用 jmap 命令手动导出,二是启动脚本中添加 -XX:+HeapDumpOnOutOfMemoryError 参数自动导出。本文中只涉及第二种。

一、内存溢出时自动导出 .hprof 文件

1.新建一个文本文件,命名为 HeapOOM.java,内容如下:

import java.util.ArrayList;
import java.util.List;

public class HeapOOM {
    static class User {}
    public static void main(String[] args) {
        List<User> list = new ArrayList<>();
        while (true) {
            list.add(new User());
        }
    }
} 

2.打开控制台,执行如下命令编译 java 文件:

javac HeapOOM.java

3.使用如下命令运行 java 文件:

java -Xms10M -Xmx10M -XX:+HeapDumpOnOutOfMemoryError -XX:HeapDumpPath=./ HeapOOM
  • -Xms10M 堆内存最小10M;
  • -Xmx10M 堆内存最大10M;
  • -XX:+HeapDumpOnOutOfMemoryError 内存溢出时自动导出堆内存快照;
  • -XX:HeapDumpPath=./ 内存快照保存位置,不指定默认当前路径

Java 内存溢出(二)使用 MAT 分析 .hprof 内存映像文件

二、下载安装 MAT

下载地址: https://www.eclipse.org/mat/downloads.php

Java 内存溢出(二)使用 MAT 分析 .hprof 内存映像文件

点击 Download。

Java 内存溢出(二)使用 MAT 分析 .hprof 内存映像文件

注意:目前最新的版本 Memory Analyzer 1.13.0 Release,是只支持在 JDK 11 下运行的

如果想下载 JDK8 下运行的版本,可以点击 Other Releases > Previous Releases。

Java 内存溢出(二)使用 MAT 分析 .hprof 内存映像文件

选择版本:Memory Analyzer 1.9.2 Release

Java 内存溢出(二)使用 MAT 分析 .hprof 内存映像文件

三、启动 MAT

双击 exe 文件启动:

Java 内存溢出(二)使用 MAT 分析 .hprof 内存映像文件

Java 内存溢出(二)使用 MAT 分析 .hprof 内存映像文件

注意: 如果 hprof 文件太大,需要调整它的内存才可以完成大 dump 文件的加载,这个配置文件需要 exe 启动后会自动生成:

Java 内存溢出(二)使用 MAT 分析 .hprof 内存映像文件

Java 内存溢出(二)使用 MAT 分析 .hprof 内存映像文件

四、MAT 分析 hprof 文件

点击 Open a Heap Dump,选择一个 hprof 文件打开:

Java 内存溢出(二)使用 MAT 分析 .hprof 内存映像文件

1.Overview 概览

概览中,我们可以看到对象所占的比例及排序。显然有个对象不正常,一共上限 10M 的内存占用了 6.9 M。

Java 内存溢出(二)使用 MAT 分析 .hprof 内存映像文件

2.Leak Suspects 溢出原因猜测

点击下方的 Leak Suspects,可以查看 MAT 的详细分析结果,猜测导致堆栈溢出的原因:

Java 内存溢出(二)使用 MAT 分析 .hprof 内存映像文件

Java 内存溢出(二)使用 MAT 分析 .hprof 内存映像文件

根据上图可以看到有一个猜测的原因:

  • 主程序占用了 92.88% 的内存,其中 Object 对象过多。

毫无疑问是对象实例过多导致的内存溢出,具体是哪个对象呢,下一步怎么分析呢?

3.Histogram 对象实例数量排序

点击下图所示柱状图(Histogram)查看对象实例数量排序,在 Regex 中可以用输入正则表达式把自己的包名,输入后回车过滤:

Java 内存溢出(二)使用 MAT 分析 .hprof 内存映像文件

Java 内存溢出(二)使用 MAT 分析 .hprof 内存映像文件

这里的 User 实例有 36w 个,显然不正常,我们可以查下是谁引用的:

Java 内存溢出(二)使用 MAT 分析 .hprof 内存映像文件

我们可以看到是 main 线程中引用了这些对象。(当前示例较为简单,如果是项目中可以明确看到是哪个类中的引用导致的)

Java 内存溢出(二)使用 MAT 分析 .hprof 内存映像文件

4.Dominator Tree 支配树

支配树: MAT 提供了一个成为支配树(Demonitor Tree)的对象图。支配树体现了对象实例间的支配关系。在对象引用图中,所有指向对象 B 的路径都经过对象 A,则认为对象 A 支配对象 B。如果对象 A 是离对象 B 最近的一个支配对象,则认为对象 A 为对象 B 的直接支配者。

支配树是基于对象间的引用图所建立的,它有以下基本性质:

  • 对象 A 的子树(所有被对象 A 支配的对象集合)标识对象 A 的保留集(Retained Set),即深堆;
  • 如果对象 A 支配对象 B,那么对象 A 的直接支配者也支配对象 B;
  • 支配树的边与对象引用图的边不直接对应。

我们可以理解为支配图就是用来查看类使用内存比例的,图中使用最多的类对应溢出原因猜测中的内存使用率 92.88%。

Java 内存溢出(二)使用 MAT 分析 .hprof 内存映像文件

以上就是 MAT 分析 .hprof 文件的常用功能。

整理完毕,完结撒花~





参考地址:

1.导出dump文件及MAT安装分析,https://blog.csdn.net/lixiangchibang/article/details/124721472

2.【JVM笔记】支配树(Dominator Tree),https://blog.csdn.net/lijibai_/article/details/126526375文章来源地址https://www.toymoban.com/news/detail-402018.html

到了这里,关于Java 内存溢出(二)使用 MAT 分析 .hprof 内存映像文件的文章就介绍完了。如果您还想了解更多内容,请在右上角搜索TOY模板网以前的文章或继续浏览下面的相关文章,希望大家以后多多支持TOY模板网!

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处: 如若内容造成侵权/违法违规/事实不符,请点击违法举报进行投诉反馈,一经查实,立即删除!

领支付宝红包 赞助服务器费用

相关文章

  • jvm内存溢出排查(使用idea自带的内存泄漏分析工具)

    想分析堆内存溢出,一定在运行jar包时就写上参数 -XX:+HeapDumpOnOutOfMemoryError ,可以看我之前关于如何运行jar包的文章。若你没有写。可以写上参数,重启你的项目,等你的项目发生下一次堆内存溢出异常,在运行的同级文件夹,将产生类似这样一个文件 java_pid74935.hprof ,若你

    2024年02月09日
    浏览(55)
  • android 如何分析应用的内存(十七)——使用MAT查看Android堆

    前一篇文章,介绍了使用Android profiler中的memory profiler来查看Android的堆情况。 如Android 堆中有哪些对象,这些对象的引用情况是什么样子的。 可是我们依然面临一个比较严峻的挑战:不管是app开发者,还是内存分析者而言,堆中的对象,非常之多,不仅有Android 原生的类,还

    2024年02月13日
    浏览(69)
  • Java读取600万行的txt文件,内存溢出解决方案

    可能造成内存溢出的原因: 一次性把txt文件读取到内存 频繁的new对象 实体类 可以使用对象池解决频繁new对象的问题 解决一次性把文件读取到内存: 可以使用文件流方式,使用java.util.Scanner类扫描文件的内容,一行一行连续地读取

    2024年04月14日
    浏览(51)
  • JVM导出内存映像(dump)文件

    JVM导出内存映像(dump)文件 什么是 dump 文件 一般来说,使用 jmap 指令生成 dump 文件的操作算得上是最常用的 jmap 命令之一,将堆中所有 存活对象导出至一个文件之中 Heap Dump 又叫做堆存储文件,指一个 Java 进程在某个时间点的内存快照。Heap Dump 在触发内存快照的时候会保存

    2024年02月14日
    浏览(37)
  • Android adb shell 查看App内存(java堆内存/vss虚拟内存/详细的内存状况/内存快照hprof)和系统可用内存

    1.adb shell 获取app 进程的pid 根据某个渠道包,去查询对应的pid,如下所示: 2.通过adb shell 查看设备的java dalvik 堆内存的最大值 执行命令行: 若是app进程中java heap(dalvik heap size) 堆内存超过384m 就会抛出oom. 若是app mainfest.xml 中设置了largeHeap=“true”,则app 进程dalvik heap limit 对应

    2024年02月15日
    浏览(57)
  • 开发笔记之:文件读取值溢出bug分析(JAVA版)

    (1)引言  以下是Java读取数据文件(FileInputStream)的代码:  其意图很简单:从当前游标位置读取一个双字(4字节)数据。 稍微复杂一点的就是一个字节序的考虑。 (2)问题  该代码做UT(单元测试)时,遇到了读取中断的问题(就是文件还没读取完就提前中断了)。

    2024年02月05日
    浏览(60)
  • jmap(Memory Map for Java)Java内存映像工具

    jmap(Memory Map for Java)命令用于生成堆转储快照(一般称为 heapdump 或 dump文件 ) 如果不使用jmap命令,要想获取Java堆转储快照也还有一些比较“暴力”的手段: 譬如 -XX:+HeapDumpOnOutOfMemoryError 参数,可以让虚拟机在内存溢出异常出现之后自动生成堆转储快照文件, 通过 -XX:

    2024年02月12日
    浏览(51)
  • java-hprof 文件是什么

    hprof 文件是 Java进程所使用的内存情况在某一时间的一次快照(Heap Profile 的缩写),格式为java_pidxxxxx*.hprof 1、所有的对象信息 对象的类信息、字段信息、原生值(int, long等)及引用值 2、所有的类信息 类加载器、类名、超类及静态字段 3、垃圾回收的根对象 根对象是指那些可以

    2024年01月25日
    浏览(32)
  • eclipse memory Analyzer(MAT) 内存泄漏分析

      1.1软件下载         Eclipse IDE,它非常有用。因为Memory Analyzer在分析堆内存的时候比较耗费内存,而Eclipse IDE本身又是比较耗费内存的,所以推荐使用独立安装的Memory Analyzer。 安装包地址:https://www.eclipse.org/mat/downloads.php 独立安装的Memory Analyzer的独立版本所需的最低Ja

    2024年02月14日
    浏览(50)
  • Java中的内存泄露、内存溢出与栈溢出

    大家好,我是欧阳方超。本次就Java中几个相似而又不同的概念做一下介绍。内存泄漏、内存溢出和栈溢出都是与内存相关的问题,但它们之间有所不同。 我们经常会遇到内存泄漏、内存溢出和栈溢出等问题,这些问题都与内存的使用有关。 内存泄漏(memory leak)指的是程序

    2024年02月03日
    浏览(67)

觉得文章有用就打赏一下文章作者

支付宝扫一扫打赏

博客赞助

微信扫一扫打赏

请作者喝杯咖啡吧~博客赞助

支付宝扫一扫领取红包,优惠每天领

二维码1

领取红包

二维码2

领红包