Java语言规范指定
在Java编程语言中,数组是对象(§4.3.1),是动态创建的,可以分配给Object类型的变量(§4.3.2)。可以在数组上调用类
Object
的所有方法。
因此,考虑到数组是对象 - 为什么Java设计者决定不允许继承和覆盖它,例如,toString()
或equals()
?
当前语法不允许创建以数组作为基类的匿名类,但我不认为 是他们决定的原因。
答案 0 :(得分:35)
Java是非对象语言和非常慢的语言之间的折衷,当时一切都是对象(想想Smalltalk)。
即使在最近的语言中,在数组(通常是地图)的语言级别具有快速结构也被视为战略目标。大多数人不喜欢数组的可继承对象的权重,当然在JVM像JIT一样推进之前没有人想要这个。
这就是为什么数组作为对象而不是设计为类实例("An object is a class instance or an array")的原因。具有覆盖阵列上的方法的能力几乎没有什么好处,当然也不足以抵消检查正确应用方法的需要(并且在我看来不是一个足以抵消的好方法)代码读取的难度增加,类似于覆盖运算符时发生的情况。)
答案 1 :(得分:16)
我遇到了 UNDER THE HOOD - Objects and arrays ,它解释了几乎所有关于JVM如何处理数组的知识。在JVM中,数组使用特殊的字节码处理,而不像我们熟悉的其他对象。
在JVM指令集中,实例化并访问所有对象 使用相同的操作码集,除之外的数组。在Java中,数组是 完整的对象,和Java程序中的任何其他对象一样, 是动态创建的。数组引用可以在任何地方使用 调用Object类型的引用,并且Object的任何方法都可以 在数组上调用。然而,在Java虚拟机中,数组是 使用特殊字节码处理。
与任何其他对象一样,数组不能声明为local 变量;只有数组引用才可以。数组对象本身始终 包含基本类型数组或对象数组 引用。如果声明一个对象数组,则会得到一个数组 对象引用。必须显式创建对象本身 使用new并分配给数组的元素。
数组是动态创建的对象,它们用作容纳(常量)相同类型对象的容器。它看起来像数组不像任何其他对象,这就是它们被区别对待的原因。
答案 2 :(得分:8)
我想指出这个article。似乎数组和对象遵循不同的操作码。我不能诚实地总结它,但是看起来,数组根本不被视为Objects
,就像我们通常习惯的那样,因此它们不会继承Object
方法。
对该帖子的作者给予全部学分,因为这是一篇非常有趣的读物,包括短片和短片。详细。
通过多个来源进一步深入研究这个主题后,我决定给出我以前答案的更精细版本。
首先要注意的是, Objects 和 Arrays 的实例化在JVM中是非常不同的,它们遵循各自的字节码。
Object
实例化遵循一个简单的操作码new
,它是两个操作数的组合 - indexbyte1
& indexbyte2
。实例化后,JVM会将引用推送到此对象的stack
。所有对象都会发生这种情况,无论其类型如何。
Array
操作码(关于数组的实例化)然而被分为三个不同的代码。
在创建涉及原始数据类型的数组时使用
newarray
- 弹出长度,分配由atype指示的新类型的基本类型,推送新数组的objectref
newarray
操作码(byte
short
char
int
long
float
{ {1}} double
)而不是对象引用。
创建对象引用数组时使用
boolean
- 弹出长度,分配由indexbyte1和indexbyte2指示的类的新对象数组,推送新数组的objectref
anewarray
操作码
分配多维数组时使用
anewarray
- 弹出维度数量的数组长度,分配由indexbyte1和indexbyte2指示的新的多维数组,推送新数组的objectref
multianewarray
指令
Object 可以是类实例或数组。
获取类实例由类实例创建表达式
显式创建
BUT
数组由数组创建表达式
显式创建
这与有关操作码的信息密切相关。数组不是开发为类接口而是由数组创建表达式显式创建,因此自然不会隐式地能够继承和/或覆盖{{1} }。
正如我们所看到的,它与数组可能包含原始数据类型的事实无关。在考虑了一些问题之后,遇到人们可能想要multianewarray
或Object
的情况并不常见,但仍然是一个非常有趣的问题,可以尝试回答。
答案 3 :(得分:2)
标准java库中有许多类不能子类化,数组不是唯一的例子。考虑String
或StringBuffer
或任何“原始包装”,例如Integer
或Double
。
JVM基于在处理这些对象时知道这些对象的确切结构(例如,对基元进行拆箱或在字节级操作数组内存)进行优化。如果你可以覆盖任何东西,那就不可能了,并且会严重影响程序的性能。