装饰器
装饰器初尝
装饰器为我们在类的声明及成员上添加标注提供了一种方式。
Javascript里的装饰器目前处在 建议征集的第二阶段,但在TypeScript里已做为一项实验性特性予以支持。装饰器是一种特殊类型的声明,它能够被附加到类声明,方法, 访问符,属性或参数上。装饰器使用
@expression这种形式expression求值后必须为一个函数,该函数会在运行时被调用(不管类是否实例化都会第一时间调用),被装饰者的信息(根据被装饰着不同而略有不同)将做为参数传入expression求值后的函数中。正所谓百闻不如一见,不再赘述装饰器的概念,而是直接写一个装饰器来感受一下。
ts
// 类装饰器使用!!!这里被装饰者是类Example
@classDecor
class Example {
// 这里为了this.text不报错,声明了所有属性都为合法属性
[x: string]: any;
print() {
console.log(this.text);
}
}
// 类装饰器声明!!!可以看到被装饰者的信息作为参数传入了,这里类装饰器的参数是被装饰类的构造函数
function classDecor(constructor: Function) {
console.log('ClassDecor is called');
constructor.prototype.text = 'Class is decorated';
}
console.log('New Example instance');
new Example().print();
// 输出什么?Bingo!
// ClassDecor is called
// New Example instance
// Class is decorated代码解析
- 这里我们定义了一个名为
classDecor的函数,该函数被@符号修饰并放置在Example类之前做为一个典型的类装饰器使用。 - 在代码的最后,我们通过调用
new Example生成一个Example实例并调用其上的print方法。 - 可以看到由于
classDecor类装饰器的存在,实例化后的print中访问到了text这个并未在Example类中定义的属性并成功打印了它的值Class is decorated。 - 另外,由于类装饰器会在程序运行的第一时间被调用,因此
ClassDecor is called会先于New Example instance被打印出来,也正是因为这个原因我们无法将text属性挂载在Example实例上(运行classDecor时还不存在该实例),取而代之我们将其挂载载了其原型链上。
russ