为什么在 Java 中是 Object 的接口子类型?
Why are interfaces subtypes of Object in Java?
为什么Java中没有Object的超接口子类型的接口?
我在这里要问的是为什么语言创建者会选择这种设计,即这种子类型化的实际目的是什么?
接口只是其子class的"specification"。他们通常不提供任何实现。所以本质上,接口是在 Java 中可以看到对象的最抽象方式。但是,Java 8 及更高版本提供了 default
和 static
方法实现,因此这使得接口更类似于抽象 classes。
由于每个对象都继承自 Object class,并且由于接口只是对象的抽象表示,因此它们也需要继承自 Object。
请注意,每个 class、抽象 class 和未明确指定它们的超级 class 的接口都被分配对象 class 作为它们的对象编译时直接super class.
这是因为对象class已经提供了一些所有对象都需要实现的方法(例如equals()
、toString()
、...)。特别有用的方法是在各种哈希表中使用的 hashCode()
,或在编写多线程程序时使用的 wait()
、notify()
和 notifyAll()
。由于继承,您几乎永远不需要显式调用这些方法,但是,如果 classes 不是从 Object 继承的,您将需要为每个 class 自己编写所有这些方法。因此,对象 class 在一定程度上减少了编程工作量。
此外,这还可以在值未知时生成 "any" 类型的参数。
void printObject(Object any) {
System.out.println("Printing object of type: " + any.getClass().getName());
System.out.println(any); // toString called "implicitly"
}
尽可能避免使用此类代码。
what is the practical purpose of this subtyping?
实际目的是您可以使用类型为接口的变量调用Object
方法,最常见的是toString()
、equals()
和hashCode()
。
为了使接口类型的变量具有非空值,必须为其分配一个对象实例。由于所有对象都扩展了 Object
,因此可以保证实现该接口的任何对象也扩展了 Object
.
例如List
是一个接口,但您可以调用 myList.toString()
,即使 toString()
没有为该接口定义。
为什么Java中没有Object的超接口子类型的接口? 我在这里要问的是为什么语言创建者会选择这种设计,即这种子类型化的实际目的是什么?
接口只是其子class的"specification"。他们通常不提供任何实现。所以本质上,接口是在 Java 中可以看到对象的最抽象方式。但是,Java 8 及更高版本提供了 default
和 static
方法实现,因此这使得接口更类似于抽象 classes。
由于每个对象都继承自 Object class,并且由于接口只是对象的抽象表示,因此它们也需要继承自 Object。
请注意,每个 class、抽象 class 和未明确指定它们的超级 class 的接口都被分配对象 class 作为它们的对象编译时直接super class.
这是因为对象class已经提供了一些所有对象都需要实现的方法(例如equals()
、toString()
、...)。特别有用的方法是在各种哈希表中使用的 hashCode()
,或在编写多线程程序时使用的 wait()
、notify()
和 notifyAll()
。由于继承,您几乎永远不需要显式调用这些方法,但是,如果 classes 不是从 Object 继承的,您将需要为每个 class 自己编写所有这些方法。因此,对象 class 在一定程度上减少了编程工作量。
此外,这还可以在值未知时生成 "any" 类型的参数。
void printObject(Object any) {
System.out.println("Printing object of type: " + any.getClass().getName());
System.out.println(any); // toString called "implicitly"
}
尽可能避免使用此类代码。
what is the practical purpose of this subtyping?
实际目的是您可以使用类型为接口的变量调用Object
方法,最常见的是toString()
、equals()
和hashCode()
。
为了使接口类型的变量具有非空值,必须为其分配一个对象实例。由于所有对象都扩展了 Object
,因此可以保证实现该接口的任何对象也扩展了 Object
.
例如List
是一个接口,但您可以调用 myList.toString()
,即使 toString()
没有为该接口定义。