2

这是相关代码的链接 - http://hg.openjdk.java.net/code-tools/jol/file/07087260ce41/jol-samples/src/main/java/org/openjdk/jol/samples/ JOLSample_16_AL_LL.java

public static void main(String[] args) throws Exception {
    out.println(VM.current().details());

    List<Integer> al = new ArrayList<Integer>();
    List<Integer> ll = new LinkedList<Integer>();

    for (int i = 0; i < 1000; i++) {
        Integer io = i; // box once
        al.add(io);
        ll.add(io);
    }

    PrintWriter pw = new PrintWriter(out);
    pw.println(GraphLayout.parseInstance(al).toFootprint());
    pw.println(GraphLayout.parseInstance(ll).toFootprint());
    pw.println(GraphLayout.parseInstance(al, ll).toFootprint());
    pw.close();
}

当我按原样运行代码时,我看到以下内容:

java.util.ArrayList@5f205aad footprint:
     COUNT       AVG       SUM   DESCRIPTION
         1      4952      4952   [Ljava.lang.Object;
      1000        16     16000   java.lang.Integer
         1        24        24   java.util.ArrayList
      1002               20976   (total)

我不确定 [Ljava.lang.Object; 的 4952 字节在哪里;来自。如果我更新 ArrayList 创建并将初始大小设置为 1000 以便没有增长,我会得到以下信息:

java.util.ArrayList@5f205aad footprint:
 COUNT       AVG       SUM   DESCRIPTION
     1      4016      4016   [Ljava.lang.Object;
  1000        16     16000   java.lang.Integer
     1        24        24   java.util.ArrayList
  1002               20040   (total)

谢谢。

更新

我关闭了 CompressedOops (-XX:-UseCompressedOops)。这是新的结果:

java.util.ArrayList@1996cd68d footprint:
 COUNT       AVG       SUM   DESCRIPTION
     1      8024      8024   [Ljava.lang.Object;
  1000        24     24000   java.lang.Integer
     1        40        40   java.util.ArrayList
  1002               32064   (total)

因此,当禁用 CompressedOops 时,参考大小会增加到 8 个字节。对我来说,Object 数组包含对 1000 个整数对象的引用更有意义。

4

1 回答 1

3

ArrayList内部由一个Object[]作为缓冲区支持,它根据需要增长

对象数组实际上是对象引用的数组。在您的情况下,看起来每个对象引用是4 bytes,因此它们的数组将使用4 * length字节,加上一些开销,例如数组的长度和其他内容

当您允许ArrayList自然增长时,缓冲区数组中任何未使用的索引默认为null,每个索引仍使用 4 个字节的内存。

ArrayList允许增长的可能已扩展到 (4952 - 16) / 4 = ~ 1234容量

ArrayList而不需要增长的只有1000个容量

于 2016-09-12T03:20:26.343 回答