Java 中 default 关键字的用途是什么?

声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow 原文地址: http://stackoverflow.com/questions/31578427/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me): StackOverFlow

提示:将鼠标放在中文语句上可以显示对应的英文。显示中英文
时间:2020-08-11 11:16:04  来源:igfitidea点击:

What is the purpose of the default keyword in Java?

javainterfacejava-8default

提问by Ravi

An interface in Java is similar to a class, but the body of an interface can include only abstract methodsand finalfields (constants).

Java 中的接口类似于类,但接口的主体只能包含抽象方法final字段(常量)。

Recently, I saw a question, which looks like this

最近看到一个问题,看起来像这样

interface AnInterface {
    public default void myMethod() {
        System.out.println("D");
    }
}

According to the interface definition, only abstract methodsare allowed. Why does it allow me to compile the above code? What is the defaultkeyword?

根据接口定义,允许抽象方法。为什么它允许我编译上面的代码?default关键字是什么?

On the other hand, when I was trying to write below code, then it says modifier default not allowed here

另一方面,当我尝试编写下面的代码时,它说 modifier default not allowed here

default class MyClass{

}

instead of

代替

class MyClass {

}

Can anyone tell me the purpose of the defaultkeyword? Is it only allowed inside an interface? How does it differ from default(no access modifier)?

谁能告诉我default关键字的用途?是否只允许在接口内?它与default(无访问修饰符)有何不同?

采纳答案by Elliott Frisch

It's a new feature in Java 8 which allows an interfaceto provide an implementation. Described in Java 8 JLS-13.5.6. Interface Method Declarationswhich reads (in part)

这是 Java 8 中的一个新特性,它允许interface提供一个实现。在 Java 8 JLS-13.5.6 中描述读取(部分)的接口方法声明

Adding a defaultmethod, or changing a method from abstractto default, does not break compatibility with pre-existing binaries, but may cause an IncompatibleClassChangeErrorif a pre-existing binary attempts to invoke the method. This error occurs if the qualifying type, T, is a subtype of two interfaces, Iand J, where both Iand Jdeclare a defaultmethod with the same signature and result, and neither Inor Jis a subinterface of the other.

添加default方法,或改变的方法,由abstractdefault,不破与预先存在的二进制兼容性,但可能会导致IncompatibleClassChangeError如果一个预先存在的二进制尝试调用的方法。如果限定类型 ,T是两个接口I和的子类型J,其中I和 都J声明了default具有相同签名和结果的方法,并且既不是I也不J是另一个的子接口,则会发生此错误。

What's New in JDK 8says (in part)

JDK 8 中的新功能说(部分)

Default methods enable new functionality to be added to the interfaces of libraries and ensure binary compatibility with code written for older versions of those interfaces.

默认方法允许将新功能添加到库的接口中,并确保与为这些接口的旧版本编写的代码的二进制兼容性。

回答by user3359139

Default methods enable you to add new functionality to the interfaces of your apps. It can also be used to have a multi inheritance. In addition to default methods, you can define static methods in interfaces. This makes it easier for you to organize helper methods

默认方法使您能够向应用程序的界面添加新功能。它也可以用于多继承。除了默认方法之外,您还可以在接口中定义静态方法。这使您可以更轻松地组织辅助方法

回答by Saurabh Gaur

A new concept is introduced in Java 8 called default methods. Default methods are those methods which have some default implementation and helps in evolving the interfaces without breaking the existing code. Lets look at an example:

Java 8 中引入了一个新概念,称为默认方法。默认方法是那些具有一些默认实现并有助于在不破坏现有代码的情况下改进接口的方法。让我们看一个例子:

 public interface SimpleInterface {
    public void doSomeWork();

    //A default method in the interface created using "default" keyword

    default public void doSomeOtherWork(){

    System.out.println("DoSomeOtherWork implementation in the interface");
       }
    }

 class SimpleInterfaceImpl implements SimpleInterface{

  @Override
  public void doSomeWork() {
  System.out.println("Do Some Work implementation in the class");
   }

 /*
  * Not required to override to provide an implementation
  * for doSomeOtherWork.
  */

 public static void main(String[] args) {
   SimpleInterfaceImpl simpObj = new SimpleInterfaceImpl();
   simpObj.doSomeWork();
   simpObj.doSomeOtherWork();
      }
   }

and the output is:

输出是:

Do Some Work implementation in the class
DoSomeOtherWork implementation in the interface


接口中的DoSomeOtherWork类实现中的Do Some Work实现

回答by sprinter

Default methods were added to Java 8 primarily to support lambda expressions. The designers (cleverly, in my view) decided to make lambdas syntax for creating anonymous implementations of an interface. But given lambdas can only implement a single method they would be limited to interfaces with a single method which would be a pretty severe restriction. Instead, default methods were added to allow more complex interfaces to be used.

默认方法被添加到 Java 8 主要是为了支持 lambda 表达式。设计者(在我看来很聪明)决定使用 lambdas 语法来创建接口的匿名实现。但是鉴于 lambdas 只能实现一个方法,它们将被限制为具有单个方法的接口,这将是一个非常严格的限制。相反,添加了默认方法以允许使用更复杂的接口。

If you need some convincing of the claim that defaultwas introduced due to lambdas, note that the straw man proposalof Project Lambda, by Mark Reinhold, in 2009, mentions 'Extension methods' as a mandatory feature to be added to support lambdas.

如果您需要对default由于 lambdas 引入的声明有一些说服力,请注意Mark Reinhold 在 2009 年提出的 Lambda 项目的稻草人提案,提到“扩展方法”是为支持 lambdas 而添加的强制性功能。

Here's an example demonstrating the concept:

这是一个演示该概念的示例:

interface Operator {
    int operate(int n);
    default int inverse(int n) {
        return -operate(n);
    }
}

public int applyInverse(int n, Operator operator) {
    return operator.inverse(n);
}

applyInverse(3, n -> n * n + 7);

Very contrived I realise but should illustrate how defaultsupports lambdas. Because inverseis a default it can easily be overriden by a implementing class if required.

我意识到非常做作,但应该说明如何default支持 lambdas。因为inverse是默认值,所以如果需要,它可以很容易地被实现类覆盖。

回答by Ahmad Sanie

The new Java 8feature (Default Methods) allows an interface to provide an implementation when its labeled with the defaultkeyword.

新的Java 8特性(默认方法)允许接口在用default关键字标记时提供实现。

For Example:

例如:

interface Test {
    default double getAvg(int avg) {
        return avg;
    }
}
class Tester implements Test{
 //compiles just fine
}

Interface Test uses the default keyword which allows the interface to provide a default implementation of the method without the need for implementing those methods in the classes that uses the interface.

Interface Test 使用 default 关键字,该关键字允许接口提供方法的默认实现,而无需在使用该接口的类中实现这些方法。

Backward compatibility:Imagine that your interface is implemented by hundreds of classes, modifying that interface will force all the users to implement the newly added method, even though its not essential for many other classes that implements your interface.

向后兼容性:假设您的接口由数百个类实现,修改该接口将强制所有用户实现新添加的方法,即使这对于实现您接口的许多其他类来说不是必需的。

Facts & Restrictions:

事实与限制:

1-May only be declared within an interface and not within a class or abstract class.

1-只能在接口中声明,不能在类或抽象类中声明。

2-Must provide a body

2-必须提供身体

3-It is not assumed to be public or abstract as other normal methods used in an interface.

3-它不像接口中使用的其他普通方法那样被假定为公共或抽象的。

回答by Riyafa Abdul Hameed

A very good explanation is found in The Java? Tutorials, part of the explanation is as follows:

The Java? 中有一个很好的解释教程,部分解释如下:

Consider an example that involves manufacturers of computer-controlled cars who publish industry-standard interfaces that describe which methods can be invoked to operate their cars. What if those computer-controlled car manufacturers add new functionality, such as flight, to their cars? These manufacturers would need to specify new methods to enable other companies (such as electronic guidance instrument manufacturers) to adapt their software to flying cars. Where would these car manufacturers declare these new flight-related methods? If they add them to their original interfaces, then programmers who have implemented those interfaces would have to rewrite their implementations. If they add them as static methods, then programmers would regard them as utility methods, not as essential, core methods.

考虑一个例子,涉及计算机控制的汽车制造商,他们发布行业标准接口,描述可以调用哪些方法来操作他们的汽车。如果这些计算机控制的汽车制造商为他们的汽车添加新功能(例如飞行)会怎样?这些制造商需要指定新方法,使其他公司(例如电子制导仪器制造商)能够将他们的软件应用于飞行汽车。这些汽车制造商会在哪里声明这些与飞行相关的新方法?如果他们将它们添加到原始接口中,那么实现了这些接口的程序员将不得不重写他们的实现。如果他们将它们添加为静态方法,那么程序员会将它们视为实用方法,而不是必不可少的核心方法。

Default methods enable you to add new functionality to the interfaces of your libraries and ensure binary compatibility with code written for older versions of those interfaces.

默认方法使您能够向库的接口添加新功能,并确保与为这些接口的旧版本编写的代码的二进制兼容性。

回答by Makoto

Something that was overlooked in the other answers was its role in annotations. As far back as Java 1.5, the defaultkeyword came about as a means to provide a default valuefor an annotation field.

在其他答案中被忽视的是它在注释中的作用。早在 Java 1.5 中,default关键字就作为为注释字段提供默认值的一种方式出现。

@Retention(RetentionPolicy.RUNTIME)
@Target(ElementType.TYPE)
public @interface Processor {
    String value() default "AMD";
}

It usage was overloadedwith the introduction of Java 8 to allow one to define a default method in interfaces.

随着 Java 8 的引入,它的用法被重载,以允许在接口中定义默认方法。

Something else that was overlooked: the reason that the declaration default class MyClass {}is invalid is due to the way that classes are declared at all. There's no provision in the language that allows for that keyword to appear there. It doesappear for interface method declarations, though.

还有一点被忽略了:声明default class MyClass {}无效的原因是由于类的声明方式。语言中没有规定允许该关键字出现在那里。不过,它确实出现在接口方法声明中

回答by Dickson the developer

Default methods in an interface allow us to add new functionality without breaking old code.

接口中的默认方法允许我们在不破坏旧代码的情况下添加新功能。

Before Java 8, if a new method was added to an interface, then all the implementation classes of that interface were bound to override that new method, even if they did not use the new functionality.

在 Java 8 之前,如果一个新方法被添加到接口中,那么该接口的所有实现类都必须覆盖该新方法,即使它们没有使用新功能。

With Java 8, we can add the default implementation for the new method by using the defaultkeyword before the method implementation.

在 Java 8 中,我们可以通过default在方法实现之前使用关键字来为新方法添加默认实现。

Even with anonymous classes or functional interfaces, if we see that some code is reusable and we don't want to define the same logic everywhere in the code, we can write default implementations of those and reuse them.

即使使用匿名类或函数式接口,如果我们看到某些代码是可重用的,并且我们不想在代码中的任何地方都定义相同的逻辑,我们可以编写这些代码的默认实现并重用它们。

Example

例子

public interface YourInterface {
    public void doSomeWork();

    //A default method in the interface created using "default" keyword
    default public void doSomeOtherWork(){

    System.out.println("DoSomeOtherWork implementation in the interface");
       }
    }

    class SimpleInterfaceImpl implements YourInterface{

     /*
     * Not required to override to provide an implementation
     * for doSomeOtherWork.
     */
      @Override
      public void doSomeWork() {
  System.out.println("Do Some Work implementation in the class");
   }

 /*
  * Main method
  */
 public static void main(String[] args) {
   SimpleInterfaceImpl simpObj = new SimpleInterfaceImpl();
   simpObj.doSomeWork();
   simpObj.doSomeOtherWork();
      }
   }