Как проверить, что Java-куча фрагментирована? - PullRequest
2 голосов
/ 05 июля 2019

У меня есть дамп кучи 29G, созданный виртуальной машиной Hotspot после OutOfMemoryError. Анализатор кучи (я использую YourKit) показал, что все объекты (включая недоступные) занимают 26G. Я думаю, что оставшиеся 3G будут потрачены впустую, потому что куча фрагментирована. Есть ли способ проверить эту теорию?

1 Ответ

3 голосов
/ 05 июля 2019

Это никак не связано с фрагментацией кучи.

Разница в размере объясняется форматом дампа кучи. Обратите внимание, что дамп кучи не является необработанным содержимым кучи - это сериализованное представление содержимого в формате HPROF .

Итак, каждый экземпляр объекта представлен HPROF_GC_INSTANCE_DUMP записью следующей структуры:

u1   record tag
u8   object ID                             
u4   stack trace serial number             
u8   class ID                       
u4   number of bytes that follow           
u1*  <field data>

Рассмотрим экземпляр java.lang.Integer. В 64-битных сжатых ООП HotSpot JVM экземпляр Integer занимает 16 байтов: 8-байтовый заголовок + 4-байтовый указатель класса + 4 байта value поле. Этот же экземпляр будет занимать 29 байт в дампе кучи, что приводит к огромным накладным расходам в 81,25%.

Конечно, куча в типичном Java-приложении обычно заполняется гораздо большими объектами, то есть массивами. Вот почему средние издержки заголовков записей HPROF кажутся меньшими, где-то около 10%, как в вашем случае.

...