美文网首页
第二十一章 修饰器

第二十一章 修饰器

作者: A郑家庆 | 来源:发表于2019-01-08 19:10 被阅读0次

    类的修饰

      修饰器是一个函数,用来修改类的行为。ES7引入了这个功能,目前Babel转码器已经支持。

    @testable
    class MyTest {}
    function testable (target) {
        target.isTestable = true
    }
    MyTest.isTestable = true
    

      上面代码中,@testable就是一个修饰器,它修改了MyTest这个类的行为,为它加上了静态属性isTestable。
      修饰器的行为基本如下。

    @decorator
    class A {}
    // 等同于
    class A {}
    A = decorator(A) || A
    

    修饰器对类的行为的改变是在代码编译时发生的,而不是在运行时。这意味着,修饰器在编译阶段运行代码。也就是说,修饰器本质就是就是编译时执行的函数。

      修饰器函数的第一个参数就是所要修饰的目标类。如果觉得一个参数不够用,可以在修饰器外面再封装一层函数。

    function testable (isTestable) {
         return function (target) {
              target.isTestable = isTestable
         }
    }
    @testable(true)
    class MyTestable {}
    MyTestable.isTestable // true
    
    @testable(false)
    class MyClass {}
    MyClass.isTestable  // false
    

      前面的例子是为类添加一个静态属性,如果想添加实例属性,可以通过目标类的prototype对象进行操作。

    function testable (target) {
         target.prototype.isTestable = true
    }
    @testable
    class MyTestable {}
    let obj = new MyTestable()
    obj.isTestable   // true
    

    方法的修饰

      修饰器不仅可以修饰类,还可以修饰类的属性。

       class Person {
          @readonly
           name () {
              return `${this.first}${this.last}`
           }
        }
        function readonly (target, name, descriptor) {
            // descriptor对象原来的值如下
            // {
            //     value: 18,
            //     enumerable: false,
            //     configurable: true,
            //     writable: true
            // }
            descriptor.writable = false
            return descriptor
        }
        readonly (Person.prototype, 'name', descriptor)
        // 类似于
        Object.defineProperty(Person.prototype, 'name', descriptor)
    

      上面的代码中,修饰器readonly用来修饰类的name方法。
      此时,修饰器函数一共可以接受3个参数,第一个参数是所要修饰的目标对象,第二个参数是所要修饰的属性名,第三个参数是该属性的描述对象。

    为什么修饰器不能用于函数

      修饰器必须写在函数上面,所以只能用于类和类的方法,不能用于函数,因为存在函数提升,类没有函数提升。

    相关文章

      网友评论

          本文标题:第二十一章 修饰器

          本文链接:https://www.haomeiwen.com/subject/hihvrqtx.html