1 class 继承

为了提高代码的重用性,提高开发效率,Scala 的 class 是支持继承的。

Scala 的继承与 Java 的继承非常类似:

(1) 单继承:

类似于 Java,Scala 也只支持单继承,一个类只能直接继承自一个父类。这意味着一个 Scala 类可以拥有一个直接的父类,就像 Java 中一样。

(2) 继承语法:

Scala 的继承语法类似于 Java,使用 extends 关键字来继承一个父类。例如:

class ChildClass extends ParentClass {

// 子类的定义

}

(3) 重写方法:

Scala 和 Java 都允许子类覆盖父类中的方法,通过使用 override 关键字来标记。例如:

class ChildClass extends ParentClass {

override def someMethod(): Unit = {

// 子类重写父类的方法

}

}

(4) 调用父类方法:

在 Scala 中,使用 super 关键字来调用父类的方法。例如:

class ChildClass extends ParentClass {

override def someMethod(): Unit = {

super.someMethod() // 调用父类的方法

// 子类的其他逻辑

}

}

下面定义了足球员类 FootballPlayer,及它的子类,进攻球员类 Striker,防守球员类 Defender:

/**

* 足球员父类

*

* @param name 球员姓名

*/

class FootballPlayer(val name: String) {

def play(): String = "Playing football"

}

/**

* 进攻球员子类

*

* @param name 球员姓名

*/

class Striker(name: String) extends FootballPlayer(name) {

override def play(): String = "Scoring goals" // 重写父类的 play 方法

def celebrate(): String = s"$name is celebrating"

}

/**

* 防守球员子类

* @param name 球员姓名

*/

class Defender(name: String) extends FootballPlayer(name) {

override def play(): String = "Defending the goal" // 重写父类的 play 方法

def tackle(): String = s"$name is making a tackle"

}

object App {

def main(args: Array[String]): Unit = {

// 测试

val striker = new Striker("Ronaldo")

println(striker.play()) // 输出 Scoring goals,调用重写后的 play 方法

println(striker.celebrate()) // 输出 Ronaldo is celebrating,调用子类的 celebrate 方法

val defender = new Defender("Sergio Ramos")

println(defender.play()) // 输出 Defending the goal,调用重写后的 play 方法

println(defender.tackle()) // 输出 Sergio Ramos is making a tackle,调用子类的 tackle 方法

}

}

运行程序,控制台输出:

Scoring goals

Ronaldo is celebrating

Defending the goal

Sergio Ramos is making a tackle

2 抽象类

在 Scala 中,抽象类是一种不能被实例化的类,它们通常用于定义一些通用的行为,但又需要子类来提供具体实现的情况。

/**

* 足球员抽象类

* @param name 球员姓名

*/

abstract class FootballPlayer(val name: String) {

/**

* 抽象方法,没有具体实现

* @return

*/

def play(): String

}

/**

* 定义实现类 Striker 继承自抽象类 FootballPlayer

* @param name 球员姓名

*/

class Striker(name: String) extends FootballPlayer(name) {

// 实现抽象方法 play

def play(): String = s"$name is scoring goals"

}

/**

* 定义实现类 Defender 继承自抽象类 FootballPlayer

* @param name 球员姓名

*/

class Defender(name: String) extends FootballPlayer(name) {

// 实现抽象方法 play

def play(): String = s"$name is defending the goal"

}

object App {

def main(args: Array[String]): Unit = {

// 定义进攻球员对象

val striker = new Striker("Ronaldo")

println(striker.play()) // 输出 Ronaldo is scoring goals

// 定义防守球员对象

val defender = new Defender("Sergio Ramos")

println(defender.play()) // 输出 Sergio Ramos is defending the goal

}

}

上面的例子中:

FootballPlayer 类是一个抽象类,包含一个抽象方法 play,没有具体的实现。Striker 类和 Defender 类是抽象类 FootballPlayer 的实现类,它们都实现了 play 方法,并提供了具体的实现。在测试部分,创建了一个 Striker 对象和一个 Defender 对象,并分别调用它们的 play 方法。

运行代码,控制台输出:

Ronaldo is scoring goals

Sergio Ramos is defending the goal

3 特质

3.1 特质介绍

Trait(特质)是 Scala 中一种非常有用的机制,可以用于定义对象的特定特征或行为。Trait类似于 Java 中的接口。

Trait 与 抽象类 是不同的:

Trait 可以被多重继承,一个类可以扩展多个 Trait,但只能继承一个抽象类。Trait 不能接受构造参数,但抽象类可以。Trait 与 抽象类 的语义不同,Trait 更适合描述对象的特征或行为,以及对象之间的 has-a 或 can-do 关系。抽象类更适合描述 is-a 关系,即子类是父类的一种特定类型。

下面是一个使用特质的例子:

/**

* 定义一个球员类

*

* @param name 球员姓名

*/

class FootballPlayer(val name: String)

/**

* 声明一个奔跑 trait

*/

trait Runner {

def run(name: String): String = s"${name} is running"

}

/**

* 声明一个得分手 trait

*/

trait Scorer {

def score(name: String): String = s"${name} is scoring goals"

}

/**

* 声明一个防守人员 trait

*/

trait Defender {

def defend(name: String): String = s"${name} is defending"

}

/**

* 创建实现类,同时继承三个 Trait

*

* @param name 球员姓名

*/

class Player(name: String) extends FootballPlayer(name) with Runner with Scorer with Defender

object App {

def main(args: Array[String]): Unit = {

// 测试

val player = new Player("Messi")

// 输出 Player is running

println(player.run(player.name))

// 输出 Player is scoring goals

println(player.score(player.name))

// 输出 Player is defending

println(player.defend(player.name))

}

}

上面的例子中:

定义了一个 FootballPlayer 类,它具有一个 name 属性,用于表示足球球员的姓名。Runner Trait 包含一个 run 方法,表示球员奔跑的行为。Scorer Trait 包含一个 score 方法,表示球员进球的行为。Defender Trait 包含一个 defend 方法,表示球员防守的行为。创建了一个名为 Player 的实现类,它继承了 FootballPlayer 类,并且同时混入了 Runner、Scorer 和 Defender 三个 Trait。在测试部分,创建了一个名为 player 的 Player 实例,并调用了它的 run、score 和 defend 方法,展示了实现类获得了这三个 Trait 中定义的行为。

3.2 对象混入特质

在 Scala 中,对象混入(Mixins)Trait 是一种非常强大和灵活的特性,它允许对象在运行时获得 Trait 中定义的行为,而无需继承 Trait 的类。对象混入 Trait 的过程就是 将 Trait 中定义的方法和属性动态地添加到对象中。

混入 Trait 可以为对象提供额外的功能,而无需改变其类层次结构。这种灵活性使得在 Scala 中,对象可以非常容易地适应不同的需求,同时保持代码的简洁和可维护性。

/**

* 定义队长特质

*/

trait Captain {

/**

* 标识是否为队长

*/

var isCaptain: Boolean = false

/**

* 判断 isCaption,输出是否为队长

*/

def hello(): Unit = {

if (isCaptain) println("I am caption") else println("I am not caption")

}

}

/**

* 球员类

* @param name 球员姓名

*/

class FootballPlayer(val name: String)

object App {

def main(args: Array[String]): Unit = {

// 实例化 FootballPlayer 时,让对象同时拥有 Captain 的相关属性、方法

val player = new FootballPlayer("Ronaldo") with Captain

player.isCaptain = true

player.hello()

}

}

在这个例子中,使用 对象混入特质 的方式,给 FootballPlayer 对象添加了队长属性。这使得我们可以非常灵活地为对象添加额外的功能,而无需修改类的层次结构。

推荐链接

评论可见,请评论后查看内容,谢谢!!!评论后请刷新页面。