对于装饰器模式的理解,可以举例。在手机上可以套上一个手机壳,不会影响手机的正常使用功能,可以给手机起到装饰的作用,并且保护手机不受到伤害。
对于装饰器模式的应用场景,比如 ES7 装饰器,core-decorators 等等。
装饰器模式的设计原则验证,将现有对象和装饰器进行分离,两者独立存在,符合开放封闭原则。
介绍
// 等同于 class Demo {} Demo = decorator(Demo) || Demo;
<a name="4LfMV"></a># 常见使用场景- 装饰类```javascript@testDecclass Demo {// ...}function testDec(target) {target.isDec = true;}alert(Demo.isDec);
- 装饰类-参数 ```javascript @testDec(true) class Demo { // … }
function testDec(isDec) { return (target) => { target.isDec = isDec; }; }
alert(Demo.isDec);
- 装饰类-mixin```javascriptfunction mixins(...list) {return (target) => {Object.assign(target.prototype, ...list);};}const Foo = {foo() {alert("foo");},};@mixins(Foo)class MyClass {}let obj = new MyClass();obj.foo();
- 装饰方法-1
```javascript
/*
- @param {*} target
- @param {*} name
- @param {*} desciptor 属性描述对象,Object.defineProperty 用到,原来值(value: specifiedFunction, enumerable: false, configurable: true, writable: true)
- @returns */ function readonly(target, name, desciptor) { desciptor.writable = false; return desciptor; }
class Person { constructor() { this.first = “A”; this.last = “B”; }
@readonlyname() {return `${this.first}-${this.last}`;}
}
let p = new Person(); console.log(p.name());
// 这里会报错,因为 name 是只读属性 // p.name = () => { // alert(“dd”); // };
- 装饰方法-2```javascript/**** @param {*} target* @param {*} name* @param {*} desciptor 属性描述对象,Object.defineProperty 用到,原来值(value: specifiedFunction, enumerable: false, configurable: true, writable: true)* @returns*/function log(target, name, desciptor) {let oldValue = desciptor.value;desciptor.value = () => {console.log(`calling ${name} width`, arguments);return oldValue.apply(this, arguments);};return desciptor;}class Math {@logadd(a, b) {return a + b;}}let math = new Math();const result = math.add(2, 4);console.log("result", result);
- core-decorators ```javascript import { deprecate } from “core-decorators”;
class Person { @deprecate facepalm() {}
@deprecate("We stopped facepalming")facepalmHard() {}@deprecate("We stopped facepalming", {url: "http://knowyourmeme.com/memes/facepalm",})facepalmHarder() {}
}
let person = new Person(); person.facepalm(); person.facepalmHard(); person.facepalmHarder();
<a name="i9iMF"></a># 装饰器模式代码示例```javascriptclass Circle {draw() {console.log("画一个圆形");}}class Decorator {constructor(circle) {this.circle = circle;}draw() {this.circle.draw();this.setRedBorder(this.circle);}setRedBorder(circle) {console.log("设置红色边框");}}// 测试代码let circle = new Circle();circle.draw();let dec = new Decorator(circle);dec.draw();
设计原理验证
- 将旧接口和使用者进行分离
- 符合开放封闭原则
