Java 接口 (interface) and Scala 特质 (trait) |
您所在的位置:网站首页 › scala的特点有哪些 › Java 接口 (interface) and Scala 特质 (trait) |
摘要:本文将简要介绍Java中的接口(interface),Java 8中接口default方法,以及Scala中的特质(trait),同时会比较Java接口与Scala特质的相似与差异。 1. Java 接口 (interface) 介绍 1.1 Java传统的接口 (interface) Java接口是一系列方法的声明,是一些方法特征的集合,一个接口只有方法的特征没有方法的实现,因此这些方法可以在不同的地方被不同的类实现,而这些实现可以具有不同的行为(功能)。 Java接口本身没有任何实现,因为Java接口不涉及表象,而只描述public行为,所以Java接口比Java抽象类更抽象化。 Java接口的方法只能是抽象的和公开的,Java接口不能有构造器,Java接口可以有public、静态的和final属性。即接口中的属性可以定义为 public static final int value=5; 假设我们有用于记录日志的Logger接口,有两种不同的实现方式,一种是输出的到Console,一种是输出到文件。 以下为参考实现: Logger接口 (interface): publicinterface Logger { //only public, static and final property is permitted publicstaticfinalintmaxLength = 50;
//only public and abstract method publicabstractvoid log(String msg); } ConsoleLogger输出到Console: publicclass ConsoleLogger implements Logger {
@Override publicvoid log(String msg) { System.out.println(msg); } } FileLogger输出到文件: publicclass FileLogger implements Logger { private PrintWriter fileOutput; public FileLogger () { try { fileOutput = new PrintWriter("app。log"); } catch (FileNotFoundException e) { e.printStackTrace(); } } @Override publicvoid log(String msg) { fileOutput.println(msg); fileOutput.flush(); } }
1.2 Java 8中的interface Java 8 允许我们使用default关键字,为接口声明添加非抽象的方法实现。 publicinterface Logger {
//only public, static and final property is permitted publicstaticfinalintmaxLength = 50;
//Java 8 interface default implementation publicdefaultvoid log(String msg) { //You could implement default log behavior here //...... } } 可以在实现类中改变它接口中的缺省行为和实现: publicclass ConsoleLogger implements Logger { //Change default log behavior here @Override publicvoid log(String msg) { System.out.println(msg); } } Java 8之后的interface可以包含包含abstract方法,也可以都是default方法。
2. Scala 特质 (trait) 介绍 Scala中的特质 (trait) 和Java 8中的接口 (interface) 比较类似,一个Scala类可以扩展一个或多个特质,Scala特质可以给出方法的缺省实现。 2.1 纯接口的特质 traitLogger { //abstract method, but no abstract declare required deflog(msg: String) } 你不需要将方法声明为abstract,特质中未被实现的方法默认就是抽象的。 //Use extends but not implements classConsoleLoggerextendsLogger { //no override required deflog(msg: String) { println(msg) } } 在重写特质的抽象方法时不需要给出override关键字 2.2 带缺省实现的特质 traitConsoleLogger {
//with implementation deflog(msg: String) { println(msg) } } 带有实现方法的特质类似于Java 8接口中的缺省方法。 以下是如何使用这个特质的示例: class Circle extends Shape withConsoleLogger { def draw() { log(“Draw a circle …”); //draw circle here …… } } 在Scala中,我们说ConsoleLogger的功能被“混入”了Circle类中。 2.3 带有特质的对象 Scala可以在创建对象时添加特质,这是Java接口所不具备的特性。 缺省的log方法什么没做:traitLogger { deflog(msg: String) { } } 下面使用这个特质的Class什么日志都不会被记录: class Circle extends Shape withLogger{ def draw() { log(“Draw a circle …”); //draw circle here } } 你可以实现一个更好的Logger特质,并在创建Circle对象是动态“混入”此特质。 traitConsoleLoggerextendsLogger { overridedeflog(msg: String) { println(msg) } } val circle1 = new CirclewithConsoleLogger 这样circle在调用draw方法时,ConsoleLogger的log方法会被执行。 类似的,你可以在另一个对象加入另外一个特质: val circle2 = new CirclewithFileLogger 2.4 叠加在一起的特质 就像Java Class可以实现多个接口一样,Scala Class也可以叠加多个特质,一般来说,特质从最后一个开始被处理。 假设有如下的Logger trait定义,分别有3个trait扩展自Logger。 traitLogger { deflog(msg: String) { } }
traitConsoleLogger extends Logger { overridedeflog(msg: String) { println(msg) } } traitTimestampLoggerextends Logger { overridedeflog(msg: String) { super.log(new Date() + “ “ + msg) } } traitShortLoggerextends Logger { val maxLength = 15 overridedeflog(msg: String) { super.log( if(msg.length |
今日新闻 |
点击排行 |
|
推荐新闻 |
图片新闻 |
|
专题文章 |
CopyRight 2018-2019 实验室设备网 版权所有 win10的实时保护怎么永久关闭 |