了解 JVM 中的对象开销

Posted

技术标签:

【中文标题】了解 JVM 中的对象开销【英文标题】:Learn about object overhead in JVM 【发布时间】:2012-06-16 06:12:28 【问题描述】:

我正在学习 java,我记得在某处读到 java 对象在 JVM 内部有一些开销,虚拟机出于管理原因使用了这些开销。所以我的问题是,谁能告诉我是否以及如何在 HotSpot JVM 中获取对象的总大小,以及它可能带来的任何开销?

【问题讨论】:

What is the memory consumption of an object in Java?的可能重复 你看***.com/questions/258120/…了吗? 我问的不是同一件事。我询问的是开销和总大小,因此我可以得出开销占总大小的百分比。 【参考方案1】:

您无法直接获得开销。开销的数量取决于实现,并且可能因许多因素而异(例如,准确的 JVM 版本,以及您使用的是 32 位还是 64 位 JVM)。

但是可以相当安全地假设,在 HotSpot 等典型的现代 JVM 实现中,每个对象的开销在 8 到 16 个字节之间。数组的开销通常比其他对象大 4 个字节(包含整数数组长度)。

另见:

In Java, what is the best way to determine the size of an object? Memory usage of Java objects: general guide

【讨论】:

【参考方案2】:

我发现this article 提供了相当多的信息,尽管我对表格中提到的一些值有一些疑问

【讨论】:

请注意,通常不鼓励仅包含链接的答案;见meta.stackexchange.com/questions/8231/…。也许你可以总结文章的相关部分。【参考方案3】:

这里是对象头、对象开销、数组头、对象引用的sn-p。希望它对某人有所帮助,如果不是 OP,因为这是一个非常古老的问题。

    private static int OBJ_HEADER;
    private static int ARR_HEADER;
    private static int INT_FIELDS = 12;
    private static int OBJ_REF;
    private static int OBJ_OVERHEAD;
    private static boolean IS_64_BIT_JVM;

     static 
    String arch = System.getProperty("sun.arch.data.model");

    IS_64_BIT_JVM = (arch == null) || arch.contains("32");
    OBJ_HEADER = IS_64_BIT_JVM ? 16 : 8;
    ARR_HEADER = IS_64_BIT_JVM ? 24 : 12;
    OBJ_REF = IS_64_BIT_JVM ? 8 : 4;
    OBJ_OVERHEAD = OBJ_HEADER + INT_FIELDS + OBJ_REF + ARR_HEADER;
       

我应该说我只知道解决方案,但我还没有弄清楚为什么会这样。这就是为什么人们应该在他们的代码中留下 cmets ......哦,好吧,当我弄清楚时,我会分享它背后的逻辑。

【讨论】:

以上是关于了解 JVM 中的对象开销的主要内容,如果未能解决你的问题,请参考以下文章

线程池 的创建小列子,以及参数的介绍

Java JVM 或 Eclipse 启动开销

jvm学习笔记二(减少GC开销的建议)

浅谈自旋锁和 JVM 对锁的优化

如何克服 python 多处理中的开销?

Java HashMap 与 ArrayList 相比的内存开销