Vue任务调度。

vue,任务调度 · 浏览次数 : 10

小编点评

1、**作用**:作用vue中一个非常重要的功能,批量更新或者叫异步更新响应式数据发生变化出发副作用函数重新执行时,我们可以去决定副作用函数的执行时机、次数和方式。 2、**例子**: ```js const state = reactive({ num: 1})effect(() => { console.log('num', state.num)})state.num++console.log('end') ``` **实现**:通过scheduler函数来实现延迟的副作用函数执行。 3、**实现可调度**:使用scheduler函数包裹副作用函数,并在副作用函数的执行前后设置标志变量。 4、**批量更新 & 异步更新**: - **num的每次变化都会导致scheduler的执行,并将注册好的副作用函数存入jobQueue队列。** - **当num被更改100次之后同步代码全部执行结束后,then回调将会被执行,此时num已经是101,而jobQueue中也只有一个fn,所以最终只会打印一次101。**

正文

1、作用

vue中一个非常重要的功能,批量更新或者叫异步更新
响应式数据发生变化出发副作用函数重新执行时,我们有能力去决定副作用函数的执行时机、次数和方式。

2、例子

const state = reactive({
  num: 1
})

effect(() => {
  console.log('num', state.num)
})

state.num++

console.log('end')

image

3、实现可调度

const state = reactive({
  num: 1
})

effect(() => {
  console.log(state.num)
}, {
  // 注意这里,假如num发生变化的时候执行的是scheduler函数
  // 那么end将会被先执行,因为我们用setTimeout包裹了一层fn
  scheduler (fn) {
    // 异步执行
    setTimeout(() => {
      fn()
    }, 0)
  }
})

state.num++

console.log('end')

通过scheduler来自主控制副作用函数的执行时机。
在这之前,执行state.num++之后,console.log(state.num)将会被马上执行,而添加scheduler后,num发生变化后将执行scheduler中的逻辑。

4、实现批量更新 & 异步更新

来看段诡异的代码,请问num会被执行多少次?100还是101?

const state = reactive({
  num: 1
})

effect(() => {
  console.log('num', state.num)
})

let count = 100

while (count--) {
  state.num++
}

image
对于页面渲染来说1到101中间的2~100仅仅只是过程,并不是最终的结果,处于性能考虑Vue只会渲染最后一次的101。

Vue是如何做到的呢?

利用可调度性,再加点事件循环的知识,我们就可以做到这件事。

  • num的每次变化都会导致scheduler的执行,并将注册好的副作用函数存入jobQueue队列,因为Set本身的去重性质,最终只会存在一个fn
  • 利用Promise微任务的特性,当num被更改100次之后同步代码全部执行结束后,then回调将会被执行,此时num已经是101,而jobQueue中也只有一个fn,所以最终只会打印一次101
 const state = reactive({
  num: 1
})

const jobQueue = new Set()
const p = Promise.resolve()
let isFlushing = false

const flushJob = () => {
  if (isFlushing) {
    return
  }

  isFlushing = true
  // 微任务
  p.then(() => {
    jobQueue.forEach((job) => job())
  }).finally(() => {
    // 结束后充值设置为false
    isFlushing = false
  })
}

effect(() => {
  console.log('num', state.num)
}, {
  scheduler (fn) {
    // 每次数据发生变化都往队列中添加副作用函数
    jobQueue.add(fn)
    // 并尝试刷新job,但是一个微任务只会在事件循环中执行一次,所以哪怕num变化了100次,最后也只会执行一次副作用函数
    flushJob()
  }
})

let count = 100

while (count--) {
  state.num++
}

image

与Vue任务调度。相似的内容:

Vue任务调度。

### 1、作用 vue中一个非常重要的功能,批量更新或者叫异步更新 响应式数据发生变化出发副作用函数重新执行时,我们有能力去决定副作用函数的执行时机、次数和方式。 ### 2、例子 ```javascript const state = reactive({ num: 1 }) effect(()

Vue - 入门

零:前端目前形势 前端的发展史 HTML(5)、CSS(3)、JavaScript(ES5、ES6):编写一个个的页面 -> 给后端(PHP、Python、Go、Java) -> 后端嵌入模板语法 -> 后端渲染完数据 -> 返回数据给前端 -> 在浏览器中查看 Ajax的出现 -> 后台发送异步请

Vue 3深度探索:自定义渲染器与服务端渲染

这篇文章介绍了如何在Vue框架中实现自定义渲染器以增强组件功能,探讨了虚拟DOM的工作原理,以及如何通过SSR和服务端预取数据优化首屏加载速度。同时,讲解了同构应用的开发方式与状态管理技巧,助力构建高性能前端应用。

Vue第三方库与插件实战手册

这篇文章介绍了如何在Vue框架中实现数据的高效验证与处理,以及如何集成ECharts、D3.js、Chart.js等图表库优化数据可视化效果。同时,探讨了Progressive Web App(PWA)的接入与优化策略,以提升Web应用的用户体验与加载速度。

理解Vue 3响应式系统原理

title: 理解Vue 3响应式系统原理 date: 2024/5/28 15:44:47 updated: 2024/5/28 15:44:47 categories: 前端开发 tags: Vue3.x TypeScript SFC优化 Composition-API Ref&Reactive

Vue 3指令与事件处理

title: Vue 3指令与事件处理 date: 2024/5/25 18:53:37 updated: 2024/5/25 18:53:37 categories: 前端开发 tags: Vue3基础 指令详解 事件处理 高级事件 实战案例 最佳实践 性能优化 第1章 Vue 3基础 1.1 V

Vue 3 组件基础与模板语法详解

title: Vue 3 组件基础与模板语法详解 date: 2024/5/24 16:31:13 updated: 2024/5/24 16:31:13 categories: 前端开发 tags: Vue3特性 CompositionAPI Teleport Suspense Vue3安装 组件

Vue 3入门指南

title: Vue 3入门指南 date: 2024/5/23 19:37:34 updated: 2024/5/23 19:37:34 categories: 前端开发 tags: 框架对比 环境搭建 基础语法 组件开发 响应式系统 状态管理 路由配置 第1章:Vue 3简介 1.1 Vue.j

VUE知识体系、VUE面试题

1. computed(计算属性)和方法有什么区别? 计算属性本质上是包含 getter 和 setter 的方法 当获取计算属性时,实际上是在调用计算属性的 getter 方法。vue 会收集计算属性的依赖,并缓存计算属性的返回结果。只有当依赖变化后才会重新进行计算。 方法没有缓存,每次调用方法都

手撕Vue-编译指令数据

经过上一篇的分析,完成了查找指令和模板的功能,接下来就是编译指令的数据了。 所以本章节主要处理的方法则是 buildElement 方法,我们先分析一下我们所拿到的数据在进行编码,这样会更加清晰一些。 我将 name, value 打印出来,分别对应的值是 name: v-model, value: