博客
关于我
强烈建议你试试无所不能的chatGPT,快点击我
JavaScript 设计模式----装饰器模式
阅读量:3948 次
发布时间:2019-05-24

本文共 3223 字,大约阅读时间需要 10 分钟。

JavaScript 设计模式----装饰器模式

1. 装饰器模式

1.1 装饰器模式介绍

  • 为对象添加新功能
  • 不改变其原有的结构和功能

1.2 装饰器模式类图

  • 传统 UML 类图
    在这里插入图片描述
  • 简化后的 UML 类图
    在这里插入图片描述

1.3 装饰器模式演示

class Circle{
draw() {
console.log('画一个圆形') }}class Decorator {
constructor(circle) {
this.circle = circle } draw() {
this.circle.draw() this.setRedBorder(circle) } setRedBorder(circle) {
console.log('设置红色边框') }}// 测试let circle = new Circle()circle.draw()let dec = new Decorator(circle)dec.draw()

1.4 装饰器模式场景

1.4.1 ES7 装饰器
  • 配置环境,安装插件
    • npm install babel-plugin-transform-decorators-legacy --save-dev
  • .babelrc 文件
{
"presets": ["es2015", "latest"], "plugins": ["transform-decorators-legacy"]}
  • 验证环境
@testDec // 装饰器class Demo {
// ...}function testDec(target) {
// target 其实就是 class Demo target.isDec = true}alert(Demo.isDec) // true
1.4.2 装饰类
  • 装饰类
// 装饰器的原理@decoratorclass A {
}// 等同于class A {
}A = decorator(A) || A;
// 可以加参数function testDec(isDec) {
return function(target) {
target.isDec = isDec; }}@testDec(true)class Demo {
// ...}alert(Demo.isDec) // true
  • 装饰类 - mixin 示例
function mixins(...list) {
return function (target) {
Object.assign(target.prototype, ...list) }}const Foo = {
foo() {
alert('foo') }}@mixins(Foo)class MyClass {
}let obj = new MyClass();obj.foo() // 'foo'
1.4.3 装饰方法
  • 装饰方法 - 例1
class Person {
constructor() {
this.first = 'A' this.last = 'B' } // 装饰方法 @readonly name() {
return `${
this.first} ${
this.last}` }}var p = new Persion()console.log(p.name())// p.name = function () {} // 这里会报错,因为 name 是只读属性
  • readonly 如何实现的
function readonly(target, name, descriptor) {
// descriptor 属性描述对象 (Object.defineProperty 中会用到), 原来的值如下 // {
// value: specifiedFunction, // enumerabel: false, // configurable: true, // writable: true, // }; descriptor.writable = false; // 关闭可写 return descriptor;}
  • 装饰方法 - 例2
class Math {
// 装饰方法 @log add(a, b) {
return a + b; }}const math = new Math();const result = math.add(2, 4); // 执行 add 时,会自动打印日志,因为有 @log 装饰器console.log('result', result);
  • log 如何实现的
function log(target, name, descriptor) {
var oldValue = descriptor.value; descriptor.value = function() {
console.log(`Calling ${
name} with`, arguments); return oldValue.apply(this, arguments); }; return descriptor;}
1.4.4 core-decorators 插件
  • 第三方开源 lib
  • 提供常用的装饰器
  • 查阅文档
  • 示例
// 首先安装 npm install core-decorators --save// 开始编码import {
readonly } from 'core-decorators'class Person {
@readonly name() {
return 'zhang' }}let p = new Person()alert(p.name())p.name = function () {
/*...*/ } // 此处会报错
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();// DEPRECATION Person#facepalm: This function will be removed in future versions.person.facepalmHard();// DEPRECATION Person#facepalmHard: We stopped facepalmingperson.facepalmHarder();// DEPRECATION Person#facepalmHarder: We stopped facepalming// See http://knowyourmeme.com/memes/facepalm for more details.

1.5 装饰器模式设计原则验证

  • 将现有对象和装饰器进行分离,两者独立存在
  • 符合开放封闭原则

转载地址:http://qcqwi.baihongyu.com/

你可能感兴趣的文章
Google's BigTable 原理 (翻译)
查看>>
MapReduce:超大机群上的简单数据处理
查看>>
设计模式笔记(转载)
查看>>
加站点加入IE的可信站点做法
查看>>
软件研发中的《破窗理论》
查看>>
敏捷的三种误区和五种改进
查看>>
用数字来看某知名B2C网站的发展内幕和隐私
查看>>
vs2010一些设置
查看>>
生活感悟语录
查看>>
用python中htmlParser实现的spider(python spider)
查看>>
在线测速网址
查看>>
mysql中GROUP_CONCAT的应用
查看>>
研发人员的绩效考核
查看>>
Python 3 之多线程研究
查看>>
Python 3中的多线程文件下载类
查看>>
Python库之MySQLdb介绍
查看>>
Python3中利用Urllib进行表单数据提交(Get,Post)
查看>>
Python开发之扩展库的安装指南及Suds(Webservice)的使用简介
查看>>
软件项目管理一点分享
查看>>
iphone程序打包ipa格式
查看>>