返回顶部
首页 > 资讯 > 前端开发 > node.js >如何理解JavaScript的设计模式
  • 782
分享到

如何理解JavaScript的设计模式

2024-04-02 19:04:59 782人浏览 薄情痞子
摘要

本篇文章为大家展示了如何理解javascript的设计模式,内容简明扼要并且容易理解,绝对能使你眼前一亮,通过这篇文章的详细介绍希望你能有所收获。  今天我们就聊一下这三个设计模式  单例模式 / 组合模

本篇文章为大家展示了如何理解javascript设计模式,内容简明扼要并且容易理解,绝对能使你眼前一亮,通过这篇文章的详细介绍希望你能有所收获。

  今天我们就聊一下这三个设计模式

  单例模式 / 组合模式 / 观察者模式

单例模式

· 什么是单例模式呢?

· 我们都知道,构造函数可以创造一个对象

· 我们 new 很多次构造函数就能得到很多的对象

· 单例模式: 就是使用构造函数实例化的时候,不管实例化多少回,都是同一个对象

· 也就是一个构造函数一生只能 new 出一个对象

· 也就是说,当我们使用构造函数,每一次 new 出来的对象 属性/功能/方法 完全一样 的时候,我们把他设计成单例模式

核心代码

· 单例模式的核心代码很简单

· 其实就是判断一下,他曾经有没有 new 出来过对象

· 如果有,就还继续使用之前的那个对象,如果没有,那么就给你 new 一个

// 准备一个构造函数// 将来要 new 的function Person() {}// 准备一个单例模式函数// 这个单例模式函数要把 Person 做成一个单例模式// 将来再想要 new Person 的时候只要执行这个 singleton 函数就可以了function singleton () {

    let instance;

    if (!instance) { // 如果 instance 没有内容        // 来到这里,证明 instance 没有内容        // 给他赋值为 new Person        instance = new Person()

    }

    // 返回的永远都是第一次 new Person 的实例    // 也就是永远都是一个实例    return instance}const p1 = singleton()const p2 = singleton()console.log(p1 === p2) // true

应用

· 我们就用这个核心代码简单书写一个 demo

// 这个构造函数的功能就是创建一个 div,添加到页面中function CreateDiv() {

    this.div = document.createElement('div')

    document.body.appendChild(this.div)}CreateDiv.prototype.init = function (text) {

    this.div.innerhtml = text}// 准备把这个 CreateDiv 做成单例模式// 让 singleton 成为一个闭包函数const singleton = (function () {

    let instance

    return function (text) {

        if (!instance) {

            instance = new CreateDiv()

        }

        instance.init(text)

        return instance

    }})()singleton('hello') // 第一次的时候,页面中会出现一个新的 div ,内容是 hellosingleton('world') // 第二次的时候,不会出现新的 div,而是原先的 div 内容变成了 world

组合模式

· 组合模式,就是把几个构造函数的启动方式组合再一起

· 然后用一个 ”遥控器“ 进行统一调用

class GetHome {

    init () {

        console.log('到家了')

    }}class OpenComputer {

    init () {

        console.log('打开电脑')

    }}class PlayGame {

    init () {

        console.log('玩游戏')

    }}

· 上面几个构造函数的创造的实例化对象的 启动方式 都一致

· 那么我们就可以把这几个函数以组合模式的情况书写

· 然后统一启动

· 准备一个 组合模式 的构造函数

class Compose {

    constructor () {

        this.compose = []

    }

    // 添加任务的方法    add (task) {

        this.compose.push(task)

    }

    // 一个执行任务的方法    execute () {

        this.compose.forEach(item => {

            item.init()

        })

    }}

· 我们就用我们的组合模式构造函数来吧前面的几个功能组合起来

const c = new Compose()// 把所有要完成的任务都放在队列里面c.add(new GetHome())c.add(new OpenComputer)c.add(new PlayGame)// 直接器动任务队列c.execute()// 就会按照顺序执行三个对象中的 init 函数

观察者模式

· 观察者模式,通常也被叫做 发布-订阅模式 或者 消息模式

· 英文名称叫做 Observer

· 官方解释: 当一个对象的状态发生改变时,所有依赖于它的对象都得到通知并被自动更新,解决了主体对象与观察者之间功能的耦合,即一个对象状态改变给其他对象通知的问题

· 听起来很迷糊,但是其实没有很难

一个例子

· 当你想去书店买书,但是恰巧今天你要买的书没有了

· 我们又不能总在书店等着,就把我们的手机留给店员

· 当你需要的书到了的时候,他会打电话通知你,你去买了就好了

· 你买到数了以后,就告诉他,我买到了,那么以后再来了书就不会通知你了

addEventListener

· 上面的例子可能还不是很明确

· 但是 addEventListener 是一个我们都用过的东西

· 这个东西其实就是一个标准的 观察者模式

btn.addEventListener('click', function () {

    console.log('btn 被点击了')})

· 上面这个就是有一个 无形的观察者 再观察着 btn 的一举一动

· 当这个 btn 被点击的时候,就会执行 对应的函数

· 我们也可以多绑定几个函数

· 说白了: 观察者模式就是我们自己实现一个 addEventListener 的功能

· 只不过 addEventListaner 只有固定的一些事件,而且只能给 dom 元素绑定

· 而我们自己写的可以随便绑定一个事件名称,自己选择触发时机而已

书写代码

· 首先我们分析功能

· 我们要有一个观察者(这里抽象为一个对象 {})

· 需要有一个属性,存放消息的盒子(把你绑定的所有事件放在里面)

· 需要一个 on 方法,用于添加事件

· 需要一个 emit 方法,用于发布事件(触发)

· 需要一个 off 方法,把已经添加的方法取消

const observer = {

    message: {},

    on: function () {},

    emit: function () {},

    off: function () {}}

· 我们把它写成一个构造函数的形式

class Observer {

    constructor () {

        this.message = {}

    }

    on () {}

    emit () {}

    off () {}}

· 现在,一个观察者的雏形就出来了

· 接下来完善方法就可以了

ON

· 先来写 ON 方法

· 添加一个事件

· 我们的 on 方法需要接受 两个参数

· 事件类型

· 事件处理函数

class Observer {

    constructor () {

        this.message = {}

    }

    on(type, fn) {

        // 判断消息盒子里面有没有设置事件类型        if (!this.message[type]) {

            // 证明消息盒子里面没有这个事件类型            // 那么我们直接添加进去            // 并且让他的值是一个数组,再数组里面放上事件处理函数            this.message[type] = [fn]

        } else {

            // 证明消息盒子里面有这个事件类型            // 那么我们直接向数组里面追加事件处理函数就行了            this.message[type].push(fn)

        }

    }

    emit () {}

    off () {}}

EMIT

· 接下来就是发布事件

· 也就是让我们已经订阅好的事件执行一下

· 同样需要接受两个参数

· 要触发的事件类型

· 给事件处理函数传递的参数

class Observer {

    constructor () {

        this.message = {}

    }

    on(type, fn) {

        // 判断消息盒子里面有没有设置事件类型        if (!this.message[type]) {

            // 证明消息盒子里面没有这个事件类型            // 那么我们直接添加进去            // 并且让他的值是一个数组,再数组里面放上事件处理函数            this.message[type] = [fn]

        } else {

            // 证明消息盒子里面有这个事件类型            // 那么我们直接向数组里面追加事件处理函数就行了            this.message[type].push(fn)

        }

    }

    emit(type, ...arg) {

        // 判断你之前有没有订阅过这个事件        if (!this.message[type]) return

        // 如果有,那么我们就处理一下参数        const event = {

            type: type,

            arg: arg || {}

        }

        // 循环执行为当前事件类型订阅的所有事件处理函数        this.message[type].forEach(item => {

            item.call(this, event)

        })

    }

    off() {}}

OFF

· 最后就是移除事件

· 就是把已经订阅的事件处理函数移除掉

· 同样需要接受两个参数

· 要移除的事件类型

· 要移除的事件处理函数

class Observer {

    constructor () {

        this.message = {}

    }

    on(type, fn) {

        // 判断消息盒子里面有没有设置事件类型        if (!this.message[type]) {

            // 证明消息盒子里面没有这个事件类型            // 那么我们直接添加进去            // 并且让他的值是一个数组,再数组里面放上事件处理函数            this.message[type] = [fn]

        } else {

            // 证明消息盒子里面有这个事件类型            // 那么我们直接向数组里面追加事件处理函数就行了            this.message[type].push(fn)

        }

    }

    emit(type, ...arg) {

        // 判断你之前有没有订阅过这个事件        if (!this.message[type]) return

        // 如果有,那么我们就处理一下参数        const event = {

            type: type,

            arg: arg || {}

        }

        // 循环执行为当前事件类型订阅的所有事件处理函数        this.message[type].forEach(item => {

            item.call(this, event)

        })

    }

    off (type, fn) {

        // 判断你之前有没有订阅过这个事件        if (!this.message[type]) return

        // 如果有我们再进行移除        for (let i = 0; i < this.message[type].length; i++) {

            const item = this.message[type][i]

            if (item === fn) {

                this.message[type].splice(i, 1)

                i--

            }

        }

    }}

· 以上就是最基本的 观察者模式

· 接下来我们就使用一下试试看

使用一下

const o = new Observer()// 准备两个事件处理函数function a(e) {

    console.log('hello')}function b(e) {

    console.log('world')}// 订阅事件o.on('abc', a)o.on('abc', b)// 发布事件(触发)o.emit('abc', '100', '200', '300') // 两个函数都回执行// 移除事件o.off('abc', 'b')// 再次发布事件(触发)o.emit('abc', '100', '200', '300') // 只执行一个 a 函数了

上述内容就是如何理解JavaScript的设计模式,你们学到知识或技能了吗?如果还想学到更多技能或者丰富自己的知识储备,欢迎关注编程网node.js频道。

--结束END--

本文标题: 如何理解JavaScript的设计模式

本文链接: https://lsjlt.com/news/82476.html(转载时请注明来源链接)

有问题或投稿请发送至: 邮箱/279061341@qq.com    QQ/279061341

猜你喜欢
  • 如何理解JavaScript的设计模式
    本篇文章为大家展示了如何理解JavaScript的设计模式,内容简明扼要并且容易理解,绝对能使你眼前一亮,通过这篇文章的详细介绍希望你能有所收获。  今天我们就聊一下这三个设计模式  单例模式 / 组合模...
    99+
    2024-04-02
  • javascript中如何理解设计模式
    本篇内容介绍了“javascript中如何理解设计模式”的有关知识,在实际案例的操作过程中,不少人都会遇到这样的困境,接下来就让小编带领大家学习一下如何处理这些情况吧!希望大家仔细阅读,能够学有所成! ...
    99+
    2024-04-02
  • 理解JavaScript设计模式中的单例模式
    单例模式(Singleton Pattern)是最简单的设计模式之一。这种类型的设计模式属于创建型模式,它提供了一种创建对象的最佳方式。 单例模式涉及到一个单一的类,该类负责创建自己...
    99+
    2024-04-02
  • JavaScript 设计模式中的代理模式详解
    前言: 代理模式,代理(proxy)是一个对象,它可以用来控制对另一个对象的访问。 现在页面上有一个香港回归最想听的金典曲目列表: <ul id="container">...
    99+
    2024-04-02
  • 理解JavaScript设计模式中的建造者模式
    我们在前面已经提过设计模式创建型模式的 3 种工厂模式 和 单例模式;本篇带来同属创建型模式的“建造者模式” 建造者模式(Builder Pattern)使...
    99+
    2024-04-02
  • 如何理解设计模式之桥模式
    本篇内容介绍了“如何理解设计模式之桥模式”的有关知识,在实际案例的操作过程中,不少人都会遇到这样的困境,接下来就让小编带领大家学习一下如何处理这些情况吧!希望大家仔细阅读,能够学有所成!举个例子桥模式的主要...
    99+
    2024-04-02
  • 如何理解command设计模式
    本篇内容介绍了“如何理解command设计模式”的有关知识,在实际案例的操作过程中,不少人都会遇到这样的困境,接下来就让小编带领大家学习一下如何处理这些情况吧!希望大家仔细阅读,能够学有所成!command...
    99+
    2024-04-02
  • javascript设计模式之代理模式
    目录一. 初识代理模式二. 代理模式的实现思想三. 代理模式分类四. 虚拟代理模式的实际运用五. 代理的使用意义及要求六. 总结一. 初识代理模式 代理模式是为一个对象提供一个代用品...
    99+
    2024-04-02
  • 如何理解Java设计模式的解释器模式
    本篇内容主要讲解“如何理解Java设计模式的解释器模式”,感兴趣的朋友不妨来看看。本文介绍的方法操作简单快捷,实用性强。下面就让小编来带大家学习“如何理解Java设计模式的解释器模式”吧!一、什么是解释器模式定义:给定一个语言,定义一个文法...
    99+
    2023-06-25
  • 如何理解Java设计模式的状态模式
    本篇内容介绍了“如何理解Java设计模式的状态模式”的有关知识,在实际案例的操作过程中,不少人都会遇到这样的困境,接下来就让小编带领大家学习一下如何处理这些情况吧!希望大家仔细阅读,能够学有所成!一、什么是状态模式定义:当一个对象的内在状态...
    99+
    2023-06-25
  • 如何理解Java设计模式的享元模式
    本篇内容介绍了“如何理解Java设计模式的享元模式”的有关知识,在实际案例的操作过程中,不少人都会遇到这样的困境,接下来就让小编带领大家学习一下如何处理这些情况吧!希望大家仔细阅读,能够学有所成!一、引言大家都知道单例模式,通过一个全局变量...
    99+
    2023-06-25
  • 如何理解Java设计模式的组合模式
    这篇文章主要介绍“如何理解Java设计模式的组合模式”,在日常操作中,相信很多人在如何理解Java设计模式的组合模式问题上存在疑惑,小编查阅了各式资料,整理出简单好用的操作方法,希望对大家解答”如何理解Java设计模式的组合模式”的疑惑有所...
    99+
    2023-06-25
  • 如何理解Java设计模式的桥接模式
    这篇文章主要讲解了“如何理解Java设计模式的桥接模式”,文中的讲解内容简单清晰,易于学习与理解,下面请大家跟着小编的思路慢慢深入,一起来研究和学习“如何理解Java设计模式的桥接模式”吧!一、什么是桥接模式桥接模式(Bridge Patt...
    99+
    2023-06-25
  • 如何理解Java设计模式的装饰模式
    这篇文章主要介绍“如何理解Java设计模式的装饰模式”,在日常操作中,相信很多人在如何理解Java设计模式的装饰模式问题上存在疑惑,小编查阅了各式资料,整理出简单好用的操作方法,希望对大家解答”如何理解Java设计模式的装饰模式”的疑惑有所...
    99+
    2023-06-25
  • 如何理解Java设计模式的单例模式
    这篇文章主要讲解了“如何理解Java设计模式的单例模式”,文中的讲解内容简单清晰,易于学习与理解,下面请大家跟着小编的思路慢慢深入,一起来研究和学习“如何理解Java设计模式的单例模式”吧!一、什么是单例模式单例模式是一种常用的软件设计模式...
    99+
    2023-06-25
  • 如何理解Java设计模式的命令模式
    本篇内容主要讲解“如何理解Java设计模式的命令模式”,感兴趣的朋友不妨来看看。本文介绍的方法操作简单快捷,实用性强。下面就让小编来带大家学习“如何理解Java设计模式的命令模式”吧!一、什么是命令模式命令模式是一个高内聚的模式,其定义为:...
    99+
    2023-06-25
  • 如何理解Java设计模式的职责链模式
    本篇内容介绍了“如何理解Java设计模式的职责链模式”的有关知识,在实际案例的操作过程中,不少人都会遇到这样的困境,接下来就让小编带领大家学习一下如何处理这些情况吧!希望大家仔细阅读,能够学有所成!一、什么是职责链模式客户端发出一个请求,链...
    99+
    2023-06-25
  • 如何理解.NET MVVM设计模式
    如何理解.NET MVVM设计模式,相信很多没有经验的人对此束手无策,为此本文总结了问题出现的原因和解决方法,通过这篇文章希望你能解决这个问题。MVVM 模式能够帮你把你程序的业务与展现逻辑从用户界面干净地分离开。保持程序逻辑与界面分离能够...
    99+
    2023-06-17
  • JavaScript设计模式学习之代理模式
    目录概述实现方法保护代理虚拟代理虚拟代理实现图片懒加载概述 代理模式属于设计模式中结构型的设计模式; 定义: 顾名思义就是为一个对象提供一个代用品或占位符,以便控制对它的访问! 白话...
    99+
    2024-04-02
  • JavaScript设计模式之策略模式详解
    什么是设计模式?为什么需要学习设计模式? 学习设计模式的目的是:为了代码可重用性、让代码更容易被他人理解、保证代码可靠性。 设计模式使代码编写真正工程化;设计模式是软件工程的基石脉络...
    99+
    2024-04-02
软考高级职称资格查询
编程网,编程工程师的家园,是目前国内优秀的开源技术社区之一,形成了由开源软件库、代码分享、资讯、协作翻译、讨论区和博客等几大频道内容,为IT开发者提供了一个发现、使用、并交流开源技术的平台。
  • 官方手机版

  • 微信公众号

  • 商务合作