您现在的位置是:亿华云 > 数据库

Vue 源码思想在工作中的应用

亿华云2025-10-04 01:00:49【数据库】9人已围观

简介一、背景由于电脑CPU、内存等的限制,能够同时启动的任务数有一定限制,例如一台电脑能够执行5个异步任务,但是目前有100个异步任务要执行,那么如何让这100个任务无间隔的快速执行完毕呢?二、问题解答刚

 

一、源用背景

由于电脑CPU、码思内存等的想工限制,能够同时启动的作中任务数有一定限制,例如一台电脑能够执行5个异步任务,源用但是码思目前有100个异步任务要执行,那么如何让这100个任务无间隔的想工快速执行完毕呢?

二、问题解答

刚遇到这个问题的作中时候,也是源用出于懵逼状态,怎么处理呢?码思??碰巧的是近期学习了一些Vue的源码知识,那么是想工不是可以借鉴其思想来解决遇到的这个难题呢?经过一步步分析,确定答案是作中肯定的。下面从解题思路、源用知识点及代码实现来聊一聊实现过程。码思

2.1 解题思路

上述是想工整个流程图,其流程可简化为以下几个步骤:

将所有任务分为两组,任务组1指的是电脑可以并行执行的亿华云异步任务,任务组2指的是其余的异步任务;

将任务组1变为可帧听状态,即其发生变化时我们能够知道;

将任务组1中的任务触发(不触发任务不会执行);

某一任务执行完毕后,将任务组2中的一个任务填充到可帧听状态的任务组1中;

任务按照固定数量不断执行,直到所有任务执行完毕。

2.2 知识点

在Vue源码中,Vue2.x使用Object.defineProperty()实现对数据的帧听;Vue3.0使用Proxy实现对数据的帧听。本着赶时髦和Proxy确实优秀的态度,在实现过程中也应用了Proxy。Proxy作为一个新的知识点,先了解一下其定义及使用方法。

2.2.1 定义

Proxy中文意思是“代理”,是在目标对象之间架设一层“拦截”,从而可以修改某些操作的默认行为。Proxy共支持十三种拦截操作:get、set、has、deleteProperty、ownKeys、getOwnPropertyDescriptor、云服务器defineProperty、preventExtensions、getPrototypeOf、isExtensible、setPrototypeOf、apply、construct。

2.2.2 简单使用

function testProxy(obj) {      return new Proxy(obj, {          get: (target, key) => {              console.log(`我被get拦截器拦截了,拦截的属性是${ key}`);         },         set: (target, key, value) => {              console.log(`我被set拦截器拦截了,拦截的属性是${ key}, 新值是${ value}`);             target[key] = value;         }     }); } const testObj = {      a: 10 }; const proxy = testProxy(testObj); proxy.a = 100; 

2.2.3 详细使用

详细用法可以参考阮一峰大佬的“ECMAScript 6入门”。

2.3 代码实现

2.3.1 定义两个任务队列

首先定义两个任务队列,task1为开始执行的一批任务,task2中为后续添加进去的任务。

const task1 = [1, 2, 3]; const task2 = [4, 5, 6, 7, 8]; 

2.3.2 数据变为可帧听的函数

利用Proxy将数据变为可帧听状态

/**  * 监听模块,监听对应数组的变化,保证其始终有一定长度的内容在运行  *  * @param { Array} initArr 定长任务的数组  * @param { Function} callback 对应的回调函数  */ function watcher(initArr, callback) {      const proxy = new Proxy(initArr, {          set(target, key, value, receiver) {              target[key] = value;             callback(value, key, receiver);         }     });     return proxy; } 

2.3.3 异步任务逻辑

/**  * 异步任务的运行逻辑  *  * @param { number} taskIndex 异步任务的序号  * @param { number} index 当前任务在定长任务的序号  * @param { Proxy} proxy Proxy实例  */ function asyncTask(taskIndex, index, proxy) {      console.log(`${ index}索引处的任务${ taskIndex}开始执行`);     return new Promise(resolve => {          setTimeout(() => {              console.log(`${ index}索引处的亿华云计算任务${ taskIndex}执行完毕`);             // 当任务队列2中还有任务时,进入队列替换任务1中执行完的任务             if (task2.length > 0) {                  proxy[index] = task2.shift();             }         }, 1000 + 2000 * Math.random());     }); } 

2.3.4 主函数

    const proxy = watcher(task1, asyncTask);     task1.forEach((taskIndex, index) => asyncTask(taskIndex, index, proxy)); } 

2.3.5 执行结果

通过结果可以看到,当一个任务完成时立刻将有一个新的任务进入。

0索引处的任务1开始执行 1索引处的任务2开始执行 2索引处的任务3开始执行 0索引处的任务1执行完毕 0索引处的任务4开始执行 2索引处的任务3执行完毕 2索引处的任务5开始执行 1索引处的任务2执行完毕 1索引处的任务6开始执行 0索引处的任务4执行完毕 0索引处的任务7开始执行 2索引处的任务5执行完毕 2索引处的任务8开始执行 1索引处的任务6执行完毕 0索引处的任务7执行完毕 2索引处的任务8执行完毕 

三、讨论

针对此类问题的处理方式,各位大佬有新的思路与方法欢迎留言,我们一起讨论,共同进步。

本文转载自微信公众号「前端点线面」,可以通过以下二维码关注。转载本文请联系前端点线面公众号。

很赞哦!(831)