js基石之---es7的decorator修飾器


es7的decorator修飾器

裝飾器(Decorator)是一種與類(class)相關的語法,用來注釋或修改類和類方法。

decorator就是給類添加或修改類的變量與方法的。

裝飾器是一種函數,寫成@ + 函數名。它可以放在類和類方法的定義前面。

 

@frozen class Foo {
  @configurable(false)
  @enumerable(true)
  method() {}

  @throttle(500)
  expensiveMethod() {}
}

 

上面代碼一共使用了四個裝飾器,一個用在類本身,另外三個用在類方法。它們不僅增加了代碼的可讀性,清晰地表達了意圖,而且提供一種方便的手段,增加或修改類的功能。

 

 

1.修改類

@addType
class human{}
function addType(target){
  target.age=27;
  target.name=hyh;
  target.sex=male;
  target.hight=178;
  console.log('此對象被修改了')
}
console.log(new human())

上面代碼中,@addType就是一個裝飾器。它修改了human這個類的行為,為它加上了靜態屬性age name sex hight等等。addType函數的參數target是human類本身。

 

2.修改類的方法

class Dabao {
    @setAttr
    cxh(){
        return true
    } 
}
function setAttr(targt, name, decorator) {
    decorator.writable = false
    return 
}

var dabao = new Dabao;
console.log(dabao.cxh)
dabao.cxh = () => {
    return false
}
console.log(dabao.cxh)

3. 裝飾器可接受多個傳參,第一個參數為修飾target  ,如果覺得一個參數不夠用,可以在裝飾器外面再封裝一層函數。

裝飾器testable可以接受參數,這就等於可以修改裝飾器的行為。

function testable(isTestable) {
  return function(target) {
    target.isTestable = isTestable;
  }
}

@testable(true)
class MyTestableClass {}
MyTestableClass.isTestable // true

@testable(false)
class MyClass {}
MyClass.isTestable // false

上面代碼中,裝飾器函數testable是在目標類的prototype對象上添加屬性,因此就可以在實例上調用。

下面是另外一個例子。

// mixins.js
export function mixins(...list) {
  return function (target) {
    Object.assign(target.prototype, ...list)
  }
}

// main.js
import { mixins } from './mixins'

const Foo = {
  foo() { console.log('foo') }
};

@mixins(Foo)
class MyClass {}

let obj = new MyClass();
obj.foo() // 'foo'

實際開發中,React 與 Redux 庫結合使用時,常常需要寫成下面這樣。

class MyReactComponent extends React.Component {}

export default connect(mapStateToProps, mapDispatchToProps)(MyReactComponent);

有了裝飾器,就可以改寫上面的代碼。

@connect(mapStateToProps, mapDispatchToProps)
export default class MyReactComponent extends React.Component {}

相對來說,后一種寫法看上去更容易理解。

 

4.裝飾器不能用於裝飾函數

5.Mixin

在裝飾器的基礎上,可以實現Mixin模式。所謂Mixin模式,就是對象繼承的一種替代方案,中文譯為“混入”(mix in),意為在一個對象之中混入另外一個對象的方法。

請看下面的例子。

const Foo = {
  foo() { console.log('foo') }
};

class MyClass {}

Object.assign(MyClass.prototype, Foo);

let obj = new MyClass();
obj.foo() // 'foo'

上面代碼之中,對象Foo有一個foo方法,通過Object.assign方法,可以將foo方法“混入”MyClass類,導致MyClass的實例obj對象都具有foo方法。這就是“混入”模式的一個簡單實現。

下面,我們部署一個通用腳本mixins.js,將 Mixin 寫成一個裝飾器。

export function mixins(...list) {
  return function (target) {
    Object.assign(target.prototype, ...list);
  };
}

然后,就可以使用上面這個裝飾器,為類“混入”各種方法。

import { mixins } from './mixins';

const Foo = {
  foo() { console.log('foo') }
};

@mixins(Foo)
class MyClass {}

let obj = new MyClass();
obj.foo() // "foo"

 


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM