基本使用

  1. class A {
  2. public name: string;
  3. private age: number;
  4. protected sex: string;
  5. constructor(name: string, age: number, sex: string) {
  6. this.name = name;
  7. this.age = age;
  8. this.sex = sex;
  9. }
  10. public getName() {
  11. return this.name;
  12. }
  13. private getAge() {
  14. return this.age;
  15. }
  16. protected getSex() {
  17. return this.sex;
  18. }
  19. }
  20. const aa = new A('wangyang', 11, 'nan');
  21. // console.log(aa);
  22. // console.log(aa.name);
  23. // console.log(aa.age); // 属性“age”为私有属性,只能在类“A”中访问
  24. // console.log(aa.sex); // 属性“sex”受保护,只能在类“A”及其子类中访问
  25. // console.log(aa.getName());
  26. // console.log(aa.getAge()); // 属性“getAge”为私有属性,只能在类“A”中访问
  27. // console.log(aa.getSex()); // 属性“getSex”受保护,只能在类“A”及其子类中访问
  28. class B extends A {
  29. city: string;
  30. constructor(name: string, age: number, sex: string, city: string) {
  31. super(name, age, sex);
  32. this.city = city;
  33. }
  34. getBName() {
  35. console.log(super.getName());
  36. }
  37. getBAge() {
  38. // console.log(super.getAge()); // 属性“getAge”为私有属性,只能在类“A”中访问
  39. // console.log(this.age); // 属性“age”为私有属性,只能在类“A”中访问s
  40. }
  41. getBSex() {
  42. console.log(super.getSex());
  43. }
  44. }
  45. const bb = new B('zhangsan', 123, '女', '杭州');
  46. bb.getBName();
  47. bb.getBSex();
  48. // bb.getSex(); // 属性“getSex”受保护,只能在类“A”及其子类中访问

image.png

protected 修饰 constuctor 构造函数之后。该类只能被子类继承。 不能被实例化。

  1. protected 修饰 constuctor 构造函数之后。该类只能被子类继承。 不能被实例化。
  2. 类似 abstract 修饰一个类 [抽象类]
  3. class A {
  4. protected constructor () {}
  5. }
  6. const a = new A() // Error: 类“A”的构造函数是受保护的,仅可在类声明中访问。ts(2674)

js 抽象类的实现

原型继承
  1. // js 抽象类
  2. function AbstraFn(name) {
  3. if (new.target === AbstraFn) {
  4. throw '抽象类不能被实例化,只能被继承';
  5. }
  6. this.name = name;
  7. }
  8. AbstraFn.prototype.abc = function () {
  9. console.log('AbstraFn 原型上的方法');
  10. };
  11. // const abstraFN = new AbstraFn('123'); // error
  12. function Child(name) {
  13. AbstraFn.call(this, name); // 构造函数继承
  14. }
  15. // 原型链继承, 父类的实例给子类的原型,还需把子类的构造函数改回来
  16. Child.prototype = Object.create(AbstraFn.prototype);
  17. console.log('123', Child.prototype.constructor); // AbstraFn 构造函数被改变了
  18. Child.prototype.constructor = Child;
  19. const child = new Child('zhangsan');
  20. console.log(child.name);
  21. child.abc();

class 继承
  1. class D {
  2. name: string;
  3. constructor(name) {
  4. if (new.target === D) {
  5. throw new Error('该类只能被子类继承');
  6. }
  7. this.name = name;
  8. }
  9. eat() {
  10. return `${this.name}`
  11. }
  12. }
  13. // const d = new D('helo');
  14. class E extends D {
  15. constructor(props) {
  16. super(props);
  17. }
  18. getProps() {
  19. console.log(super.eat());
  20. }
  21. }
  22. const e = new E('world');
  23. e.getProps();

readonly

  1. class A {
  2. public readonly name: string
  3. constructor(name: string) {
  4. this.name = name
  5. }
  6. }
  7. const a = new A('zhangsan')
  8. a.name = 'lisi' // Error

可选属性

  1. class A {
  2. public name: string
  3. public age?: number
  4. constructor (name:string, age?: number, public sex?: string) {
  5. this.name = name
  6. this.age = age
  7. }
  8. }
  9. const a = new A('张三')
  10. const b = new A('李四', 18)
  11. const c = new A('王五',20, 'male')
  12. console.log(a) // A {sex: undefined, name: "张三", age: undefined}
  13. console.log(b) // A {sex: undefined, name: "李四", age: 18}
  14. console.log(c) // A {sex: "male", name: "王五", age: 20}

抽象类 & 抽象方法

  1. abstract class A {
  2. constructor(public name: string) {}
  3. abstract getName(): string;
  4. }
  5. // const a = new A () // 无法创建抽象类的实例。ts(2511)
  6. class B extends A {
  7. constructor(name: string) {
  8. super(name);
  9. this.name = name;
  10. }
  11. public getName() { // 抽象的方法必须实现
  12. return this.name;
  13. }
  14. }
  1. abstract class A {
  2. abstract _name:string
  3. abstract get insideName():string
  4. abstract set insideName(val: string): string // error 不能标记 返回值 类型。
  5. abstract func ():void
  6. }

implements 类继承接口

  1. interface Food {
  2. type:string,
  3. size:number
  4. }
  5. class Tomoto implements Food {
  6. type: string
  7. size: number
  8. constructor(type: string, size: number) {
  9. this.type = type
  10. this.size = size
  11. }
  12. }
  13. # 接口 检测的是该类实例化的 对象
  14. // 也就是
  15. class Tomoto implements Food { //Error: 类型 "Tomoto" 中缺少属性 "type",但类型 "Food" 中需要该属性。ts(2420)
  16. public static type: string
  17. public size: number = 10
  18. }

接口继承类

接口继承一个类后,会继承该类的成员,但是 不包括其实现 ( 即只继承他的成员 和 成员类型)。接口还会继承private,protected 修饰的成员。当接口继承了 有这2个修饰符修饰的成员后,该接口只能被 该类,或者该类的子类 使用。

  1. class A {
  2. private name:string = ''
  3. }
  4. interface I extends A {}
  5. class B implements I {} // Error: 类型 "B" 中缺少属性 "name",但类型 "I" 中需要该属性。
  6. class B implements I {
  7. private name: string = '' // Error: 类“B”错误实现接口“I”。 类型具有私有属性“name”的单独声明。ts(2420)
  8. }
  9. class B extends A implements I {}

泛型中使用类

  1. const create = <T>(c: new () => T): T => new c();
  2. class A {
  3. public name: string = 'HELLO';
  4. }
  5. const a = create<A>(A);
  6. console.log(a.name);
  7. ------------------------------------------------------------
  8. const create = <T> (c: new(param:number)=> T, param: number): T=> new c(param)
  9. class A{
  10. public age: number
  11. constructor(age:number) { this.age = age}
  12. }
  13. create<A>(A, 11)