前言
今天在学习中对于装饰器感觉比较陌生,于是百度查了一下Decorator的用法,特意在此记录一下。
须知
由于目前并不直接支持Decorator,因此需要先安装babel-plugin-transform-decorators-legacy
yarn add babel-plugin-transform-decorators-legacy babel-core babel-polyfill --dev
同时修改.babelrc文件
{
"plugins": ["transform-decorators-legacy"]
}
-
简介
装饰器(Decorator)是一种与类(class)相关的语法,用来注释或修改类和类方法。许多面向对象的语言都有这项功能,目前有一个提案将其引入了 ECMAScript。
装饰器是一种函数,写成@ + 函数名
。它可以放在类和类方法的定义前面。
-
类的装饰
装饰器可以用来修饰整个类
@test
class Boy{
}
function test(target){
target.age=10
}
console.log(Boy.age)//10
上面是给class加静态属性,同样可以给class加实例属性,可以通过目标类的prototype对象操作。
@test
class Boy{
}
function test(target){
target.prototype.age=10
}
const luck=new Boy();
console.log(luck.age)//10
如果参数不够用,可以在装饰器外层再封装一层函数
@test(11)
class Boy{
}
function test(age){
return function(target){
target.prototype.age=age;
}
}
const luck=new Boy();
console.log(luck.age)//11
-
装饰方法
class Boy{
@log
add(a,b){
return a+b
}
}
function log(target,name,descriptor){
let oldValue=descriptor.value;
descriptor.value=function(){
console.log(`calling ${name} with`,arguments);
return oldValue.apply(this,arguments)
}
return descriptor
}
const math =new Boy();
console.log(math.add(2,3))
//calling add with [Arguments] { '0': 2, '1': 3 }
//5
装饰器第一个参数是类的原型对象,上例是Boy.prototype,装饰器的本意是要“装饰”类的实例,但是这个时候实例还没生成,所以只能去装饰原型(这不同于类的装饰,那种情况时target参数指的是类本身);第二个参数是所要装饰的属性名,第三个参数是该属性的描述对象。
-
Mixin
在装饰器的基础上,可以实现Mixin模式。将一个对象混入另外一个对象。
const Foo={
foo(){
console.log('foo')
}
}
function mixins(list){
return function (target) {
Object.assign(target.prototype,list);
};
}
@mixins(Foo)
class MyClass {}
let obj = new MyClass();
obj.foo()
网友评论