首页 > 代码库 > [Java][MAT] Shallow Heap大小计算释疑

[Java][MAT] Shallow Heap大小计算释疑

查看Mat文档时里面是这么描述Shallow Heap的:Shallowheap is the memory consumed by one object. An object needs 32 or 64 bits(depending on the OS architecture) per reference, 4 bytes per Integer, 8 bytesper Long, etc. Depending on the heap dump format the size may be adjusted (e.g.aligned to 8, etc...) to model better the real consumption of the VM.

照这么说,在Android机子上,每个Object的Shallow Heap开销应该是8 bytes 再加上该对象每个内部成员变量的内存开销。

 

   Class Demo0 {}
 
   Class Demo1 {
       intint_num = 0;
   }

以上面两个类为例,Demo0的对象ShallowHeap大小应该是8bytes,那么Demo1Shallow Heap大小应该是8 + 4 = 12bytes。但MAT的结果却显示值为16 bytes,如下图:

 

图1. Demo1 Shallow Heap值显示

 

 

为了解决以上疑问,继续在类里面添加成员变量观察ShallowHeap的显示大小。

   Class Demo12 {
       int int_num= 0;
       int int_num1= 0;
   }
 
   Class Demo13 {
       int int_num= 0;
       int int_num1= 0;
       int int_num2= 0;
   }

上面这两个类的对象中,Shallow Heap 对应的大小如图2所示分别为

Demo12 : 16 bytes;

Demo13: 24 bytes;


图2.

 

 

至此,就由不得猜想JVM在分配内存时是以8 bytes为粒度进行分配的了。

Google一下得文章:Java对象内存结构,英文版JavaObjects Memory Structure。

由此猜想得到验证。

由于对象是以8 bytes为粒度进行分配的,所以Demo1仅仅用去一个4bytes的int,仍空余着另外的4bytes,这空余的4bytes可以再声明第2个int成员变量变成Demo12。如果要再声明第3个int成员变量时,需要再另外分配出8bytes的空间,即变为24bytes的Demo13了。

 

   由此问题发现,VM为一个对象所分配的空间,并不一定是当前这个对象中成员变量所占内存的大小和,极可能是偏大的。

 

   另附各种数据类型所需的字节数如下表。

  

类型

bytes

long

8

int

4

short

2

char

2

boolean

1

byte

1

ref(引用)

4

 

[Java][MAT] Shallow Heap大小计算释疑