1. 基础 :
(1)在尽可能不改变类(对象)结构的情况下,扩展其功能 ;
(2)启用装饰器模式 : experimentalDecorators:true ;
(3) 装饰器是一种特殊类型的声明,它可以被附加到类声明、属性、方法、参数或访问符上 ;
(4) 装饰器函数:
1. 我们要在一个类或方法上使用装饰器,首先需要提供一个装饰器函数,这个函数会在该装饰器被使用的时候调用 ;
2. 使用装饰器:在需要被装饰的类或方法前通过 @装饰器名称 来调用装饰器 ;
装饰器可以累加,可以一行也可以多行书写 ;
3. 形式:
@A @B
@C
class Person {}
(5)类装饰器:
1. 类装饰器应用于构造函数,可以用来监视、修改或替换类定义;
2. 类的构造函数会作为类装饰器函数的唯一一个函数 function f(constructor: Function) {};
/* 类装饰器 */
function f(constructor: Function) {}
// 修改构造函数
function f<T extends {new(...args: any[]):{}}>(constructor: T) {
return class extends constructor {
age: number = 35;
}
}
// 装饰器工厂函数
function f(arg: Object) {
return function<T extends {new(...args: any[]):{}}>(constructor: T) {
return class extends constructor {
age: number = arg.age;
}
}
}
@f({age: 35})
2. 装饰器 - 案例 1:
npm init
npm i typescript ts-node
/* tsconfig.json 配置 */
// experimentalDecorators:true 启用装饰器
{
"compilerOptions": {
"module": "ES2015",
"target": "es2017",
"outDir": "./dist",
"noImplicitThis": true,
"strictNullChecks": true,
"experimentalDecorators": true
},
"include": [
"./src/**/*"
]
}
// src/1.ts
// 定义一个 装饰器Age , 参数类型为T(构造函数,可接受数组,返回一个对象)
function Age<T extends { new(...args: any[]): {} }>(constructor: T): T {
class Person2 extends constructor {
age: number = 10;
}
return Person2;
}
// Age是一个装饰器函数,该函数会自动调用,不需要加()调用,调用的时候会传入下面这个对应的class的构造函数
@Age
class Person {
username = 'kimoo'
}
let p1 = new Person();
console.log(p1); // Person2 { username: 'kimoo', age: 10 }
// 实例化的p1 具有 Person类的属性 以及 装饰器@Age 的属性
// 运行 1.ts 查看结果
.\node_modules\.bin\ts-node .\src\1.ts
3. 装饰器 - 案例 2:
function Age(v: number) {
return function <T extends { new(...args: any[]): {} }>(constructor: T): T {
class Person2 extends constructor {
age: number = v;
}
return Person2;
}
}
@Age(10) // 利用 闭包 实现 装饰器 传参
class Person {
username = 'Kimoo'
}
@Age(20)
class Cat {
username = '小猫咪'
}
let p1 = new Person();
console.log(p1);
let c1 = new Cat();
console.log(c1);