Dart学习笔记(三)

1、Dart中的类

  • 概念
    1.Dart中的所有东西都是对象,所有对象都是继承自Object类。
    2.一个类通常是由属性方法组成
  • 创建一个类
class Person {
  String name;
  int age;
  // 默认构造函数,注意:参数都是必填!
  Person(this.name, this.age);
  // 或者,可选参数
  Person([this.name, this.age]);
  // 或者,命名可选参数,一般都是用这种
  Person({this.name, this.age});
  //
  void printInfo() {
    print('${this.name} + ${this.age}');
  }
}
// 运行
// 参数都是必填,必须按顺序填写
Person p = Person('Singx', 18);
p.printInfo();
// 可选参数,必须按顺序填写,后面的可以不填写
Person p = Person('Singx');
p.printInfo();
// 命名可选参数,按命名对应填空
Person p = Person(age: 18);
p.printInfo();

//打印结果
Singx + 18
Singx + null
null + 18
  • 命名构造函数
class Person {
  String name;
  int age;
  //命名构造函数
  Person.create(String namee, int agee) {
    this.name = namee;
    this.age = agee;
  } //这里不能写`;`
  //
  void printInfo() {
    print('${this.name} + ${this.age}');
  }
}
// 运行
Person p = Person.create('Singx', 18);
p.printInfo();

//打印结果
Singx + 18
  • 私有方法私有属性,在方法名和属性名前加一个_即可。
class Person {
  String _name;
  int _age;
  void _printInfo() {
  }
}
  • get set 关键字
class Person {
  String name;
  int age;
  Person(this.name, this.age);
  // 返回值写最前面,不能这样:get String nameAndAge
  String get nameAndAge {
    return 'nameAndAge: ${this.name} + ${this.age}';
  }
  // 调用方法不能这样:p.newName( 'Cindy');
  set newName(String value) {
    this.name = value;
  }
}
// 运行
Person p = Person('Singx', 18);
print(p.nameAndAge);
p.newName = 'Cindy';
print(p.nameAndAge);

// 打印结果
nameAndAge: Singx + 18
Cindy + 18
  • 构造函数体之前初始化实例变量
class Person {
  String name;
  int age;
  // 实际开发中很少用这种方式,但是要知道,防止大佬耍骚你看不懂
  Person(/*这里面不能填*/) : name = 'Singx', age = 18 {
    print('${this.name} + ${this.age}');
  }
}
  • 类的静态变量静态方法,变量名或方法名最前面添加static修饰
class Person {
  static String name;
  static void printName(){
    //这里不能通过this.name访问
    print(name);
  }
}
运行,直接通过类名点语法访问,不需要实例化
Person.name;
Person.printName();
  • 类的对象的操作符: ?. as is ..
    1. ?. :判断对象是否为null,为null就不继续执行,不为null就执行.后面的方法。
    class Person {
      void func(){
        print('this is func');
      }
    }
    // 运行
    Person p;
    p?.fun();
    // 运行结果
    `无任何打印`
    
    // 运行
    p = Person();
    p?.fun();
    // 运行结果
    this is func
    
    1. as:类型转换,重命名第三方库类名
    2. is:类型判断
    3. ..:联级操作符
    class Person {
    String name;
    int age;
    void printInfo(){
        print('${this.name} + ${this.age}');
      }
    }
    // 运行
    Person p= Person();
    p..name = 'Singx'
     ..age = 18
     ..printInfo();
    // 运行结果
    Singx + 18
    

2、类的继承

  • 子类使用extends关键词来继承父类
  • 类会继承父类里面可见的属性和方法,但是不会继承构造函数
  • 子类能复写父类的方法,gettersetter
class Animal {
  String name;
  void eat() {
    print('${this.name} eat...');
  }
}
class Dog extends Animal {
  @override //重写标志,可以不写,但最好还是写了
  void eat(){
    super.eat(); //调用父类的方法
    print('${this.name} eattt...');
  }
}
// 运行
Dog dog = Dog();
dog.name = 'dog';
dog.eat();
// 运行结果
dog eat...
dog eattt...

3、抽象类

  • Dart中的抽象类主要用于定义标准,给子类开放接口。
    1. 通过abstract关键词定义。
    2. 抽象方法:没有方法体。
    3. 抽象类的子类必须要实现抽象类里的抽象方法。
    4. 抽象类不能被实例化,只有继承它的子类可以。
abstract class Animal {
  String name;
  void eat(); //抽象方法
}
class Dog extends Animal {
  void eat() {
    print('${this.name} eat...');
  }
}
  • extendsimplements区别
    1. 如果要复用抽象类里面的方法,并且要用抽象方法约束自类的话我们就用extends继承抽象类。
    2. 如果只是把抽象类当做标准的话我们就用implements实现抽象类。

4、多态

  • 父类定义一个方法不去实现,让继承他的子类去实现,每个子类有不同的表现。
class Animal {
  void eat() {
    print('Animal eat...');
  }
}
class Dog extends Animal {
  @override
  void eat() {
    print('Dog eat...');
  }
}
class Cat extends Animal {
  @override
  void eat() {
    print('Cat eat...');
  }
}
// 运行
Animal ani = Dog();
ani.eat();
Animal ani1 = Cat();
ani1.eat();
// 运行结果
Dog eat...
Cat eat...

5、Mixins混入

  • Mixins能实现类似多继承的功能,但它不是多继承。
  • 作为Mixins的类只能继承自Object类,不能继承其他类。
  • Mixins类不能有构造函数
  • 一个类可以混入多个Mixins
class Monster with Dog, Cat {}

class Dog {
  String name = 'Dog';
  eatShit() {
    print('eatShit...');
  }

  run() {
    print('dog run...');
  }
}

class Cat {
  String name = 'Cat';
  eatFish() {
    print('eatFish...');
  }

  run() {
    print('cat run...');
  }
}
// 运行
Monster m = Monster();
m.eatShit();
m.eatFish();
m.run();
print(m.name);
// 运行结果
eatShit...
eatFish...
cat run...
Cat
  • 以上代码可以得出:
    1. Mixins类可以用with连接,混入多个用,隔开。
    2. Monster类可以访问Dog/Cat类所有公开的属性和方法,不会访问私有的属性和方法(这不废话嘛...)。
    3. DogCat中有同名的属性和方法时,Monster访问该属性和方法时取决于with Dog, Cat的顺序,即最后面的属性或方法会覆盖前面的同名属性或方法(有点啰嗦啊,理解就行...)。

6、泛型

  • 泛型就是解决方法接口的复用性,以及对不特定数据类型的支持(类型校验)。
// 一般写法1,可以传入任意类型,不会进行类型校验,安全性和代码可读性都较低。
getValue (value) {
  return value; 
}
// 一般写法2,只能传入特定类型,兼容性不高。
int getValue (int value) {
  return value; 
}
// 泛型写法,可传入任意类型,会进行类型校验,兼容性、安全性、可读性都有了,干得漂亮!
// T代表一种类型,当然可以用任意单个大写的字母代替,比如:A、B、C...。
T getValue<T> (T value) {
  return value; 
}
// 运行
var a = getValue<int>(10);
print(a);
// 运行结果
10
最后编辑于
©著作权归作者所有,转载或内容合作请联系作者
【社区内容提示】社区部分内容疑似由AI辅助生成,浏览时请结合常识与多方信息审慎甄别。
平台声明:文章内容(如有图片或视频亦包括在内)由作者上传并发布,文章内容仅代表作者本人观点,简书系信息发布平台,仅提供信息存储服务。

相关阅读更多精彩内容

友情链接更多精彩内容