1

我是功能界面的新手,今天我从几个教程网站学习。我有一个问题请提供您的建议并指导我。

下面提到的代码对我有一个问题。

@FunctionalInterface
interface Demo {
    Object clone();   // protected
    //int hashCode();              // public
    //boolean equals(Object c); // public
    //public void wait(); // final so we cannot override this one.
}

对象类是所有 java 类的父类。这里的 wait() 方法说没有被覆盖,因为这是最终的。所以这意味着 Demo 接口也是 Object 类的子类(一般而言)。

> @FunctionalInterface means interface with exact one method declaration.

问题:所以,现在代码在Object clone(); 方法没有注释。所以意味着这个方法是在接口 Demo 中声明的。但是当我们点击它的实现时,我们会移动到 Object 类的 clone() 方法。

当我们注释clone()方法和取消注释equals()方法时,我们得到编译时错误,接口不是FunctionalInterface。为什么 ??????以及为什么它与 clone() 方法的功能接口。

请不要说 clone() 是受保护的,如果克隆在 Object 类中受保护是怎么回事。请为我解释。

谢谢,萨维

4

2 回答 2

2

这是因为clone()受到保护。我知道你让我不要那样说,但我还是要说,因为这就是答案。

http://docs.oracle.com/javase/specs/jls/se8/html/jls-9.html#jls-9.8具体说:

对于接口 I,令 M 是作为 I 成员的一组抽象方法,它们与 Object 类的任何公共实例方法没有相同的签名。那么,如果在 M 中存在一个方法 m 并且满足以下两个条件,则 I 是一个函数式接口:

m 的签名是 M 中每个方法签名的子签名(第 8.4.2 节)。

对于 M 中的每个方法,m 都是可替换的返回类型(第 8.4.5 节)。

请注意,它说的是公共实例。当您取消注释clone()时,这是一个与公共实例方法没有相同签名的方法,因为clone()inObject是一个受保护的实例方法。因此,您的clone()方法将满足条件。你不能这么说equals(),因为equals()它是一个公共实例方法Object。这意味着该规则所指的集合M为空,因此该集合中必须存在的方法m不存在。

JLS 中有一段评论在下面几段中解释了为什么他们决定clone()区别对待。

于 2016-11-22T06:28:54.053 回答
0

由于public boolean equals(Object c)已经存在于Object,Demo不声明任何新方法。要成为一个FunctionalInterface,它应该只声明一个方法。

相反,当您声明public Object clone()时,它是一种新方法,因为原始方法Objectprotected. 因此它可以被认为是一个FunctionalInterface

于 2016-11-22T06:26:07.503 回答