Dart中的混入类mixin

介绍

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{
  @override
  void fly() => print("fly");

  @override
  void swim() => print("swim");

  @override
  void walk() => print("walk");

}
class Cat extends Animal implements Walk{
  @override
  void walk() => print("walk");
}
class Dove extends Animal implements Walk,Fly{
  @override
  void fly() => print("fly");

  @override
  void 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{
  @override
  run() {
    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{
  @override
  run() {
    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 - 简书

猜你喜欢

转载自blog.csdn.net/TDSSS/article/details/129123887