Eclipse Memory Analyzer分析堆文件技巧

一、巧用OBJECTS获取Map对象中的key和每个key使用的retainedHeapSize

OBJECTS是一个关键字,用来“扁平化”(flatten)一个对象数组 / 引用数组 /对象集合,使得你可以把“一个数组 / 列表 /子查询返回的集合”中的每一个元素当作单独一行来处理

举例:

现在想要获取CamundainstanceCache中存储了哪些key,且每一个keyretainedHeapSize应该如何获取?

image-20250924165742046

1、选中cache行执行OQL

1
SELECT * FROM OBJECTS 1529719

image-20250924170004006

从执行结果来说,返回了ConcurrentHashMap实例本身以及所保留的内存

2、调整select结果,获取map中的元素项

在获取map实例中具体的元素项的时候,就需要使用OBJECTS进行扁平化展开

1
SELECT objects o.table.@referenceArray FROM OBJECTS 1529719 o 
  • 通过.获取对象属性,此处tableConcurrentHashMap的一个属性
  • @referenceArray 是一个用于访问 对象引用数组 的内建属性

image-20250924170214350

此时已经获取到map实例中存储的每个key以及所保留的内存,但是由于key本身还是存储在Node中无法直观查看,需要进一步调整语句获取Node对象中的具体属性

3、使用嵌套查询获取Node对象中的属性

嵌套查询结果也是一个列表,需要使用OBJECTS平铺展开

1
SELECT toString(s.key) AS key, s.@retainedHeapSize FROM OBJECTS ( SELECT OBJECTS o.table.@referenceArray FROM OBJECTS 1529719 o  ) s 
  • @retainedHeapSize 是一个 内建属性(Bean 属性 / OQL attribute),用来表示某个对象的 Retained Heap 大小
  • toString是用来将key的结果转为字符串输出
  • s.key中的keyNode对象的属性,也可以用来获取Node中的valhash等属性

image-20250924171124031

Shallow Heap Size vs Retained Heap Size

  • Shallow Heap(也叫 usedHeapSize / @usedHeapSize)是对象自身在内存中占用的大小,不包括它引用子对象的那部分。
  • Retained Heap@retainedHeapSize)则包括这个对象及其控制/支配(如果这个对象被回收时,子对象也可回收)的子对象占用的内存。
  • 举例来说,如果对象 A 引用 B 和 C,且 B 和 C 没有被别的对象引用,那么 A 的 @retainedHeapSize = A 的 shallow + B 的 shallow + C 的 shallow

Eclipse Memory Analyzer分析堆文件技巧
https://probiecoder.cn/java/mat_usage.html
作者
duwei
发布于
2025年9月24日
许可协议