“新”关键字有什么作用

2022-09-03 04:39:09

我正在在线学习Java教程,试图学习这门语言,它在使用数组的两个语义之间跳动。

long results[] = new long[3];
results[0] = 1;
results[1] = 2;
results[2] = 3;

和:

long results[] = {1, 2, 3};

本教程从未真正提到为什么它在两者之间来回切换,所以我在这个主题上搜索了一下。我目前的理解是,运算符正在创建一个“长头数组”类型的对象。我不明白的是,我为什么想要这样,这样做的后果是什么?new

  • 是否有某些特定于“数组”的方法不适用于数组,除非它是“数组对象”?
  • 有没有我不能用“数组对象”做什么,而我对普通数组可以做?
  • Java VM 是否必须对使用运算符初始化的对象进行清理,而这通常不需要这样做?new

我来自C,所以我的Java术语在这里可能不正确,所以如果某些事情无法理解,请要求澄清。


答案 1

在Java中,所有数组和对象都分配在堆上,因此从某种意义上说,所有数组都是“数组对象”。在 Java 中,在堆栈上分配的唯一内容是对象引用和基元。其他所有内容都是在堆中定义和分配的对象,包括数组,而不管您使用哪种语法来声明它。(您的两个示例在最终结果中是等效的,请参阅 JLS §10.3 及其链接部分,了解有关每个示例的实际分配和分配方式的更多信息。

这与 C/C++ 相反,在 C/C++中,您可以显式控制堆栈和堆分配。

请注意,Java在短期对象分配/解除分配方面非常快。它非常高效,因为它具有基于生成的垃圾回收器。因此,要回答您的问题:

是否有某些特定于“数组”的方法不适用于数组,除非它是“数组对象”?有没有我不能用“数组对象”做什么,而我对普通数组可以做?

没有数组不是对象,所以没有。但是,有些方法不适用于基元数组。采用 的方法在未首先将其转换为 .这是由于Java 5及更高版本中自动装箱的一些实现细节。Object[]long[]Long[]

Java VM 是否必须对使用运算符初始化的对象进行清理,而这通常不需要这样做?new

分配的任何内容最终都必须被垃圾回收,所以在做任何事情方面,它通常不会做?不。但是,请注意,在C / C++中,使用/分配数组意味着您还必须/it,这在Java中不必这样做,因为它会为您回收数组。newmallocnewfreedelete []

请注意,如果在方法中声明了您的,并且您从不将其存储在方法外部的引用中,则在方法调用结束时,它将自动标记为垃圾回收。垃圾回收器将等待回收其空间,直到它需要它,但您不必通过(或和对象的析构函数)自己进行任何回收。long[]delete []delete

编辑:一些承诺的参考资料:


答案 2

Java 中的关键字将创建一个新对象。在这种情况下,它正在创建一个数组...这是一个对象。new

这两种形式是等同的。第二个只是第一个的方便速记。它是句法糖

是否有某些特定于“数组”的方法不适用于数组,除非它是“数组对象”?

所有数组都是对象。时期。

有没有我不能用“数组对象”做什么,而我对普通数组可以做?

见上文。

Java VM 是否必须对使用 new 运算符初始化的对象进行清理,而这通常不需要执行?

不。就 JVM 而言,以不同方式创建的对象之间没有区别。