返回

揭秘 Dart 中神秘的类:解开对象导向编程的密码

Android

Dart 中的类:对象导向编程的基石

构造函数:对象的诞生

类的构造函数是创造对象的大门。当您使用 new 创建对象时,构造函数会初始化对象的属性,使其达到初始状态。Dart 允许您定义多个构造函数,每个函数都可以接受不同的参数。

class Person {
  String name;
  int age;

  // 默认构造函数
  Person() {
    name = "John Doe";
    age = 25;
  }

  // 带参数的构造函数
  Person.withName(this.name) {
    age = 25;
  }
}

成员可见性:私密与公开

Dart 中的类成员有不同的可见性等级,这控制了它们的可访问范围。

  • public: 成员可以在任何地方访问,包括类的外部。
  • private: 成员只能在定义它们的类内部访问。
  • protected: 成员只能在定义它们的类及其子类中访问。
class Person {
  String name; // public
  int _age; // private
  String get fullName => "$name $_age"; // public getter
  void set fullName(String value) { // public setter
    name = value.split(" ")[0];
    _age = int.parse(value.split(" ")[1]);
  }
}

getter 和 setter:间接访问

getter 和 setter 允许您间接访问类成员,从而提供额外的控制和灵活性。getter 以方法的形式获取成员的值,而 setter 以方法的形式设置成员的值。

class Person {
  String name;
  int age;

  String get fullName => "$name $age";

  set fullName(String value) {
    name = value.split(" ")[0];
    age = int.parse(value.split(" ")[1]);
  }
}

初始化列表:初始化快捷方式

初始化列表提供了一种简便的方法来初始化类成员,它在构造函数中使用。初始化列表中的每个条目都将成员变量初始化为给定的值。

class Person {
  String name;
  int age;

  Person(this.name, this.age);
}

static 静态成员:类级元素

静态成员属于类本身,而不是其特定实例。它们可以通过类名直接访问,无需创建类的实例。静态成员通常用于存储与类相关的信息或提供类级功能。

class Person {
  static const String species = "Homo sapiens";

  static String greet() => "Hello from Person class";
}

继承:类的进化

继承允许一个类(子类)从另一个类(父类)继承其属性和方法。子类可以重写父类的方法并添加自己的新成员,从而创建更具体的类层次结构。

class Animal {
  String name;
  int age;

  Animal(this.name, this.age);

  String makeSound() => "Animal sound";
}

class Dog extends Animal {
  Dog(String name, int age) : super(name, age);

  @override
  String makeSound() => "Woof woof";
}

抽象类:定义行为的蓝图

抽象类定义了一个接口,子类必须实现该接口。抽象类不能被实例化,它们的作用是提供一个规范,强制其子类实现特定的方法。

abstract class Shape {
  double get area;

  void draw();
}

class Rectangle implements Shape {
  double width;
  double height;

  Rectangle(this.width, this.height);

  @override
  double get area => width * height;

  @override
  void draw() {
    print("Drawing a rectangle");
  }
}

多态:形状变换

多态允许子类对象以与父类对象相同的方式被处理。当调用父类方法时,将调用子类重写的版本,从而实现动态的行为。

class Animal {
  String name;

  Animal(this.name);

  void speak() {
    print("$name says something");
  }
}

class Dog extends Animal {
  Dog(String name) : super(name);

  @override
  void speak() {
    print("$name barks");
  }
}

class Cat extends Animal {
  Cat(String name) : super(name);

  @override
  void speak() {
    print("$name meows");
  }
}

void main() {
  List<Animal> animals = [Dog("Buddy"), Cat("Kitty")];

  for (Animal animal in animals) {
    animal.speak(); // 多态行为
  }
}

接口:契约约束

接口定义了一组方法和属性,强制实现该接口的类提供这些方法和属性的实现。接口与抽象类类似,但它们不能定义字段或实现方法。

interface Drawable {
  void draw();
}

class Rectangle implements Drawable {
  double width;
  double height;

  Rectangle(this.width, this.height);

  @override
  void draw() {
    print("Drawing a rectangle");
  }
}

Mixins:灵活的组合

Mixins 允许您将多个类中的行为组合到一个类中,而无需继承。Mixins 使用 with 关键字添加到类中,它们可以提供额外的功能而不破坏类层次结构。

mixin Flyable {
  void fly() {
    print("Flying");
  }
}

class Bird {
  String name;

  Bird(this.name);

  void sing() {
    print("$name is singing");
  }
}

class FlyingBird extends Bird with Flyable {
  FlyingBird(String name) : super(name);

  @override
  void sing() {
    super.sing();
    fly();
  }
}

结论

Dart 中的类是构建复杂系统和组织代码的强大工具。通过理解类的构造函数、成员可见性、getter 和 setter、初始化列表、static 静态成员、继承、抽象类、多态、接口和 Mixins 等概念,您可以驾驭对象导向编程的力量。

掌握 Dart 中类的奥秘将使您能够创建更模块化、更可重用和更易于维护的代码。随着您的实践和深入,您将发现类的真正潜力,并解锁 Dart 编程的无限可能性。

常见问题解答

  • 什么是构造函数?
    构造函数是用于创建新对象的类方法。

  • getter 和 setter 有什么区别?
    getter 和 setter 是访问和修改类成员的间接方式。getter 以方法形式返回成员值,而 setter 以方法形式设置成员值。

  • 继承有什么好处?
    继承允许类重用父类的功能,并通过添加新功能来扩展它们。

  • 抽象类与接口有什么区别?
    抽象类提供了一个接口,但可以实现方法,而接口仅定义方法和属性,不能实现方法。

  • Mixins 的作用是什么?
    Mixins 允许您将功能添加到类中,而无需创建子类。