我正在检查我的应用程序的堆转储。该应用有一个java.util.concurrent.ConcurrentHashMap
,其中Key类型为java.lang.String
,value为用户定义的类,其中byte[]
字段。
我添加了16000个密钥,每个密钥有30个字符,值的字节数组是3000个字节。所以我希望并发hashmap的整体保留堆大小为48MB(16000 * 3000)。
但堆转储中的值是24MB。当我进一步检查时,我发现有很多条目如下。这些条目具有HashMap节点的保留大小远小于键和值的保留大小之和。
如何理解这种差异?
Class Name | Shallow Heap | Retained Heap
----------------------------------------------------------------------------------------------------------------------
[5490] java.util.concurrent.ConcurrentHashMap$Node @ 0x6c6a23910 | 32 | 136
|- <class> class java.util.concurrent.ConcurrentHashMap$Node @ 0x6c71bc320 System Class| 0 | 0
|- key java.lang.String @ 0x6c6a23930 /data-node-3-10/parent2/child2 | 24 | 104
|- val org.apache.zookeeper.server.DataNode @ 0x6c6a23998 | 32 | 3,304
----------------------------------------------------------------------------------------------------------------------
PS:我的任务是找到系统配置和内存使用之间的关联。
编辑:对于许多其他条目,值如下所示。 HashMap节点(3160)的保留大小包含节点的密钥(128)+值(3000)的保留大小。 但是对于某些条目(例如,如上所示),对于具有键和值的节点而言,它似乎不正确(136)。保留的大小分别为104和3304.
Class Name | Shallow Heap | Retained Heap
----------------------------------------------------------------------------------------------------------------------
[9706] java.util.concurrent.ConcurrentHashMap$Node @ 0x6c6a1ab98 | 32 | 3,160
|- <class> class java.util.concurrent.ConcurrentHashMap$Node @ 0x6c71bc320 System Class| 0 | 0
|- key java.lang.String @ 0x6c6a1abb8 /data-node-0-10/parent1/child2/grandchild1 | 24 | 128
|- val org.apache.zookeeper.server.DataNode @ 0x6c6a1ac38 | 32 | 3,000
----------------------------------------------------------------------------------------------------------------------