Warning: file_get_contents(/data/phpspider/zhask/data//catemap/9/java/347.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Java 最大的阵列需要多少内存?_Java_Arrays_Memory - Fatal编程技术网

Java 最大的阵列需要多少内存?

Java 最大的阵列需要多少内存?,java,arrays,memory,Java,Arrays,Memory,我想获得在Java中创建尽可能大的数组所需的确切内存量 我的测试计划: public class MemoryOfArraysTest { public static void main(String... args) { Object[] array = new Object[Integer.MAX_VALUE - 2]; } } 通过自己的测试,我知道数组的最大长度是Integer.MAX_VALUE-2(2147483645) 如果该数字较大,则会出现以下

我想获得在Java中创建尽可能大的数组所需的确切内存量

我的测试计划:

public class MemoryOfArraysTest {
    public static void main(String... args) {
        Object[] array = new Object[Integer.MAX_VALUE - 2];
    }
}
通过自己的测试,我知道数组的最大长度是
Integer.MAX_VALUE-2
(2147483645)

如果该数字较大,则会出现以下错误:

Exception in thread "main" java.lang.OutOfMemoryError: Requested array size exceeds VM limit
at MemoryOfArraysTest.main(MemoryOfArraysTest.java:3)
但这只是接近阵列最大长度的一步。另一个问题是虚拟机可以使用的内存。您可以使用指定内存

如果我使用
java-Xmx1g MemoryOfArraysTest
(只有1GB内存)运行我的类,我会得到预期的错误:

Exception in thread "main" java.lang.OutOfMemoryError: Java heap space
at MemoryOfArraysTest.main(MemoryOfArraysTest.java:3)
如果我使用
java-Xmx10g MemoryOfArraysTest
(10GB内存)运行它,它就可以正常工作


这就是我目前所拥有的。但是我的程序需要多少内存呢?最好是KB的。有没有可能计算它的方法?

每个对象有两个头,使用
XX:+UseCompressedOops
(默认为启用),这两个头将有
12个字节。加上
4个字节
,以保持数组的长度。再加上一些你需要考虑的最终填充

你可以用它来了解它有多大。这样的实验:

    Object[] array = new Object[100];
    for(int i=0;i<100;++i){
        array[i] = new Object();
    }

    System.out.println(GraphLayout.parseInstance(array).totalSize());

这是一个非常酷的概念,但是为什么?Integer.MAX_VALUE-2==2147483646个元素。在具有
-XX:+UseCompressedOops
(默认值)的64位VM上,引用需要4个字节。OpenJDK上当前的数组头占用16个字节(注意,Zing和OpenJ9可能不同,project最终会出现),因此2147483646*4+16个字节。但是为什么呢?很少需要知道这一点。你在解决什么问题,你想达到什么目的?事实上不可能找到答案。至少,这是不可行的。您无法知道类加载器加载的其他类占用了多少堆空间(例如,所有java.lang垃圾)。如果不知道这一点,你就不知道还有多少堆留给你。默认情况下加载的内容所使用的堆的确切数量在JDK的几乎每个构建版本之间都会略有不同。旁注:最大可能的数组是
long[]
double[]
,因为每个条目将占用
64
位或
8
字节。使用可能的最大数组大小(
Integer.MAX_VALUE=2^31-1
)进行计算会产生略大于
16
GB(
17179869192
字节)的大小,因为它没有真正的用例。我不想创建这样一个长度的数组。我只是好奇什么是等式,以及Java中通常如何管理数组。但我认为这样问不会得到回答。因为我的问题不是很清楚。感谢所有的评论和答案。它们有助于我更好地理解内存的主题。我的mac上有
32GB
的RAM,即使我尝试增加交换,我的mac在尝试计算该大小的填充数组时也会关闭
Object[] array = new Object[Integer.MAX_VALUE - 2];
System.out.println(ClassLayout.parseInstance(array).instanceSize());