使用多个混入
本课属于 Coddy Dart 学习旅程的“面向对象编程”单元。第 52 课,共 110 课。
就像你可以实现多个接口一样,也可以将多个混入应用到单个类中。只需在 with 关键字后列出它们,并用逗号分隔。
mixin Swimming {
void swim() => print('Swimming');
}
mixin Flying {
void fly() => print('Flying');
}
mixin Walking {
void walk() => print('Walking');
}
class Duck with Swimming, Flying, Walking {
void quack() => print('Quack!');
}
void main() {
var duck = Duck();
duck.swim(); // 来自 Swimming 混入类
duck.fly(); // 来自 Flying 混入类
duck.walk(); // 来自 Walking 混入类
duck.quack(); // 来自 Duck 类
}当混入类中有同名方法时,顺序很重要。列表中的最后一个混入类优先:
mixin A {
void greet() => print('Hello from A');
}
mixin B {
void greet() => print('Hello from B');
}
class MyClass with A, B {}
void main() {
MyClass().greet(); // 输出:Hello from B
}由于 B 排在 A 后面,因此优先使用它的 greet() 方法。这种分层行为让你可以组合出具备所需功能的类,从多个来源整合功能,而不必构建复杂的继承层次结构。
挑战
简单让我们使用混入构建一个智能家居设备系统,将多种功能组合起来。你将创建代表不同智能功能的混入,然后构建一个同时使用它们的设备。
你将把代码整理到两个文件中:
smart_features.dart:定义三个混入,分别提供不同的智能家居功能:- 一个
VoiceControl混入,其中包含方法voiceCommand(String command),用于打印Voice: [command] - 一个
WiFiEnabled混入,其中包含方法connectWiFi(String network),用于打印Connected to [network] - 一个
PowerSaver混入,其中包含用于打印Entering sleep mode...的方法enterSleepMode(),以及用于打印Waking up!的方法wakeUp()
SmartSpeaker类。添加一个带构造函数的String name属性,并加入方法playMusic(String song),用于打印[name] playing: [song]- 一个
main.dart:导入智能功能文件,并演示扬声器如何组合所有功能:- 创建一个名为
'Echo'的SmartSpeaker - 调用
connectWiFi('HomeNetwork') - 调用
voiceCommand('Play jazz') - 调用
playMusic('Smooth Jazz Mix') - 调用
enterSleepMode() - 调用
wakeUp()
- 创建一个名为
只需使用一个 with 子句,SmartSpeaker 就能获得全部三个混入中的方法。这展示了多个混入如何让你组合所需的功能,而不必使用复杂的继承结构。
预期输出:
Connected to HomeNetwork
Voice: Play jazz
Echo playing: Smooth Jazz Mix
Entering sleep mode...
Waking up!亲手试试
import 'smart_features.dart';
void main() {
// TODO: 创建一个名为 'Echo' 的 SmartSpeaker 对象
// TODO: 调用 connectWiFi('HomeNetwork')
// TODO: 调用 voiceCommand('Play jazz')
// TODO: 调用 playMusic('Smooth Jazz Mix')
// TODO: 调用 enterSleepMode()
// TODO: 调用 wakeUp()
}
这节课包含一个小测验。开始学习即可作答,并记录你的进度。
面向对象编程中的所有课
自己练习: Dart 在线编译器