本站消息

站长简介/公众号

  出租广告位,需要合作请联系站长


+关注
已关注

分类  

暂无分类

标签  

暂无标签

日期归档  

2024-11(6)

前端Vue之发布订阅模式 前端vue之发布订阅模式

发布于2023-03-17 06:07     阅读(982)     评论(0)     点赞(4)     收藏(0)


目录

1.什么是发布订阅模式

2.实现简单的发布订阅

3.收集更新函数

4.触发更新函数

5.总结


一个响应式数据可能会有多个视图部分都需要依赖,也就是响应式数据变化之后,需要执行的更新函数可能不止一个,对于这种情况,有必要学习一下发布订阅模式。

1.什么是发布订阅模式

发布订阅模式定义了一种一对多的依赖关系,让多个订阅者对象同时监听某一个主题对象。这个主题对象在自身状态变化时,会通知所有订阅者对象,使它们能够自动更新自己的状态。(盗用一张图)

 现实生活中有很多类似的例子,比如我最近在网上看上一双鞋子,联系到卖家后,这双鞋已经卖光了,于是问卖家什么时候有货,卖家告诉我,要等一个星期后才有货,可以收藏店铺,等有货的时候再通知,所以我收藏了此店铺,但与此同时,其他人等也喜欢这双鞋,也收藏了该店铺;等来货的时候就依次会通知他们。这就是简单的发布订阅。

  • 指定发布者
  • 给发布者添加一个缓存列表,用于存放回调函数以便通知订阅者
  • 最后发布消息的时候,发布者遍历缓存列表,依次触发里面存放的订阅者回调函数

2.实现简单的发布订阅

先从dom绑定事件来说,一般一个事件绑定一个回调函数,但是也可以绑定多个回调函数。只不过方式不同,第二种就可以绑定多个。

  1. dom.οnclick=function(){}
  2. dom.addEventListener('click',()=>{})

实现简单的发布订阅

  1. // 增加dep对象 用来收集依赖和触发依赖
  2. const dep = {
  3. map: Object.create(null),
  4. // 收集
  5. collect(dataProp, updateFn) {
  6. if (!this.map[dataProp]) {
  7. this.map[dataProp] = []
  8. }
  9. this.map[dataProp].push(updateFn)
  10. },
  11. // 触发
  12. trigger(dataProp) {
  13. this.map[dataProp] && this.map[dataProp].forEach(updateFn => {
  14. updateFn()
  15. })
  16. }
  17. }

3.收集更新函数

用于更新dom的更新函数集中起来

  1. // 编译函数
  2. function compile() {
  3. let app = document.getElementById('app')
  4. // 1.拿到app下所有的子元素
  5. const nodes = app.childNodes // [text, input, text]
  6. //2.遍历所有的子元素
  7. nodes.forEach(node => {
  8. // nodeType为1为元素节点
  9. if (node.nodeType === 1) {
  10. const attrs = node.attributes
  11. // 遍历所有的attrubites找到 v-model
  12. Array.from(attrs).forEach(attr => {
  13. const dirName = attr.nodeName
  14. const dataProp = attr.nodeValue
  15. console.log(dirName, dataProp)
  16. if (dirName === 'v-text') {
  17. console.log(`更新了${dirName}指令,需要更新的属性为${dataProp}`)
  18. node.innerText = data[dataProp]
  19. // 收集更新函数
  20. dep.collect(dataProp, () => {
  21. node.innerText = data[dataProp]
  22. })
  23. }
  24. })
  25. }
  26. })
  27. }

4.触发更新函数

当属性变化时,通过属性找到对应的更新函数列表

  1. function defineReactive(data, key, value) {
  2. Object.defineProperty(data, key, {
  3. get() {
  4. return value
  5. },
  6. set(newValue) {
  7. // 更新视图
  8. if (newValue === value) return
  9. value = newValue
  10. // 再次编译要放到新值已经变化之后只更新当前的key
  11. dep.trigger(key)
  12. }
  13. })
  14. }

5.总结

这是在vue框架之下的发布订阅,其原理中提到了几个专业名词

  1.  observe 对象指的是把数据处理成响应式的对象
  2.  watcher 指的其实就是数据变化之后的更新函数 (vue中的watcher有两种,一种是用来更新视图的watcher,一种是通过watch配置项声明的watcher)
  3.  dep 指的就是使用发布订阅实现的收集更新函数和触发更新函数的对象

发布订阅模式的本质是解决一对多的问题,在vue中实现数据变化之后的精准更新。

                                                 vue作者编程功力之深厚,运用之巧妙,令人叹服!!!!!!

                              

原文链接:https://blog.csdn.net/weixin_44178497/article/details/128439702




所属网站分类: 技术文章 > 博客

作者:92wwhehjw

链接:http://www.qianduanheidong.com/blog/article/505496/4e7ae4780dd58bac88fc/

来源:前端黑洞网

任何形式的转载都请注明出处,如有侵权 一经发现 必将追究其法律责任

4 0
收藏该文
已收藏

评论内容:(最多支持255个字符)