Java对象内存使用情况 – ibm jvm 1.4.2

是否有可能在应用程序中找到java中对象的内存使用情况?

我希望在应用程序运行时将对象内存使用作为调试输出的一部分。 我不想使用外部应用程序连接到VM。

我有一个问题,即很少有类占用大量内存并导致内存问题,我的应用程序崩溃了。 我需要找到内存使用情况(我正在使用有限的内存资源)。

编辑:我使用的是java 1.4:/

看我的宠物项目MemoryMeasurer 。 一个很小的例子:

long memory = MemoryMeasurer.measureBytes(new HashMap()); 

您还可能获得更多定性内存细分:

 Footprint footprint = ObjectGraphMeasurer.measure(new HashMap()); 

例如,我使用后者来导出各种数据结构的每个条目的成本 ,其中开销是以创建的对象的数量,引用和基元来衡量的,而不仅仅是字节(这也是可行的)。 因此,下次使用(默认) HashSet ,可以通知您其中的每个元素都需要1个新对象(不是您的元素),5个引用和一个int,这与HashMap的条目完全相同(不出意外,因为任何HashSet元素都在HashMap结束),依此类推。

您可以在任何对象图上使用它。 如果您的对象图包含您希望忽略的其他结构的链接,则应使用谓词来避免探索它们。

编辑 Instrumentation不适用于Java 1.4(哇,人们仍然使用它?!),因此上面的memoryBytes调用对你不起作用。 但第二个会。 然后你可以写这样的东西(如果你在32位机器上):

 long memory = footprint.getObjects() * 8 + footprint.getReferences() * 4 + footprint.getPrimitives().count(int.class) * 4 + footprint.getPrimitives().count(long.class) * 8 + ...; 

这给你一个近似值。 一个更好的答案是将其细化到16的最接近的倍数:

 long alignedMemory = (x + 15) & (~0xF); //the last part zeros the lowest 4 bits 

但答案可能仍然是关闭的,因为如果你发现16个布尔值,如果它们被发现在同一个对象中则是一回事,如果它们分布在多个对象中则是另一回事(并且由于对齐而导致过多的空间使用) 。 这个逻辑可以作为另一个访问者实现(类似于MemoryMeasurer和ObjectGraphMeasurer的实现 – 很简单,你可能会看到),但我没有打扰,因为这就是Instrumentation所做的,所以它只能理解1.5以下的Java版本。

Eclipse MAT是分析内存的一个非常好的工具。

有jdk附带的工具,如jmap和jhat,它们提供了对象级细节。

下面的链接提供了一段计算对象大小的Java代码:

http://www.javaworld.com/javaworld/javatips/jw-javatip130.html