介绍
Mixin 是一种在多重继承中复用某个类中代码的方法模式。
Mixin 是面向对象程序设计语言中的类,提供了方法的实现。其他类可以访问mixin
类的方法、变量而不必成为其子类。
简单来说就是官方设计了一个种可以方便复用的类,不必去实现很多接口。
应用场景
比如说这里有一个Anmal的超类,下面有三个子类分别是Mammal、Bird、Fish,在其下还有更多的子类。
这里我们拿三个类来实例,分别是Duck、Cat、Dove,其中Duck三种方法都会,Cat会walk,Dove会walk和fly,如果要用继承来实现的话如下:
abstract class Animal{}
abstract class Swim{void swim();
}
abstract class Walk{void walk();
}
abstract class Fly{void fly();
}class Duck extends Animal implements Swim,Walk,Fly{@overridevoid fly() => print("fly");@overridevoid swim() => print("swim");@overridevoid walk() => print("walk");}
class Cat extends Animal implements Walk{@overridevoid walk() => print("walk");
}
class Dove extends Animal implements Walk,Fly{@overridevoid fly() => print("fly");@overridevoid walk() => print("walk");
}
void main(){Duck().swim();Duck().walk();Duck().fly();Cat().walk();Dove().fly();Dove().walk();
}
输出的结果如下:
因为dart也是单继承语言,这种用法和java中是完全一样的,但是接口中所有的方法都要重写就很冗余,有没有一种办法我们可以复用接口里的方法呢,这时就可以来使用mixin了。
我们用mixin来代替接口,想要重用mixin类的方法只需要在类后面加上with关键字即可,如下:
abstract class Animal{}mixin Swim{void swim() => print("swim");
}
mixin Walk{void walk() => print("walk");
}
mixin Fly{void fly() => print("fly");
}class Duck extends Animal with Swim,Walk,Fly{}
class Cat extends Animal with Walk{}
class Dove extends Animal with Walk,Fly{}void main(){Duck().swim();Duck().walk();Duck().fly();Cat().walk();Dove().fly();Dove().walk();
}
最后打印出来的结果是上面完全一致的,想要实现类中特例的方法也和接口的使用方法是一样的,直接重写就行。
进阶用法
mixin的线性化特性
如果我们混入的类中,存在相同的方法,会怎么调用呢?比如在Person类和A类中都定义了run()方法,我们在Male类中调用试一试
class Person{ run() => print("person"); }mixin A{ run() => print("A"); }class Male extends Person with A{}main(){Male().run();
}
结果如下:
-------------------------------------------------------------------------------------------------------
A
这里只执行了A类中的run()方法,在dart中,有一种叫做线性化的语法特性
上面mixin的代码等同于
Class PersonA = Person with A
Class Male extends PersonA;
相当于Person类中的run()方法被A重写了,所以调用的是A类里的重写后的run()方法。
那我们有办法调用Person类中的方法吗?答案当然是可以的,而且很简单,既然是继承,我们直接调用父方法就行了,加上super.run()
class Person{ run() => print("person"); }mixin A{@overriderun() {super.run();print("A");}
}class Male extends Person with A{}main(){Male().run();
}
输出结果为:
person
A
on
在使用mixin的时候可以用on关键字来限制,在混入该类的时候必须先继承或混入on后面的类
如:
class Person{ run() => print("person"); }mixin A{ run() => print("A"); }mixin C on Person{@overriderun() {super.run();print("C");}
}//这里还可以是
//class Femal extends Person with A,C{}class Female with A,Person,C{} //混入时,Person类必须在C之前main(){Female().run();
}
最后输出
person
C
参考
dart中的mixin解析_进击的Summer的博客-CSDN博客_dart mixin
深入理解 Dart 中的 Mixin - 简书