JavaScript实现锁功能,同一时间多次异步请求函数都取到返回值,只触发一次异步请求 您所在的位置:网站首页 js返回一个函数怎么操作 JavaScript实现锁功能,同一时间多次异步请求函数都取到返回值,只触发一次异步请求

JavaScript实现锁功能,同一时间多次异步请求函数都取到返回值,只触发一次异步请求

2023-08-11 22:36| 来源: 网络整理| 查看: 265

问题

有个需求,某个异步请求函数可能被多次调用,重复调用消耗资源,需要对其进行优化

每次调用该函数都能取到返回值只发送一次异步请求

这个和节流、防抖功能不一样,节流防抖会丢弃掉中间的请求,中间的请求获取不到返回值,这里要求每一个函数调用都能取到返回值。

方案一

很容易想到使用同步非阻塞方案,在第一个点击时,进入loading状态,之后的点击判断loading就等50毫秒继续检查loading的值,直到loading为false,返回localEnv。这里使用setTimeout来模拟异步请求。

async function clickMe() { const env = await getEnv() console.log(env) } let localEnv let loading = false async function getEnv() { if (localEnv) { return localEnv } // 若正在请求中,则每50毫秒检查loading状态,直到为false,返回请求结果 if (loading) { // 同步非阻塞 while(loading) { await wait(50) } return localEnv } else { loading = true return new Promise((resolve, reject) => { console.log('questing env......') setTimeout(() => { localEnv = { platform: '141001', appid: 'aoshdakhpa8fkdng' } loading = false resolve(localEnv) }, 2000) }) } } function wait (time) { return new Promise(resolve => { setTimeout(() => { resolve() }, time) }) }

在这里插入图片描述

方案一主要由于循环去检测loading的状态,导致不那么高效

方案二

Java中可以通过锁机制,使用wait/notify轻易实现该功能。JavaScript也可以利用锁机制来实现类似wait/notify的功能。 JavaScript可以通过resolve/reject函数来实现锁,在没有调用resolve/reject函数时,promise会看起来相当于一直阻塞(其实和Java的阻塞不一样,这里只是没有执行后续的函数)。

async function clickMe() { const env = await getEnv() console.log(env) } let localEnv, p const queue = [] let loading = false async function getEnv() { return new Promise((resolve, reject) => { if (localEnv) { resolve(localEnv) } // 进入这个if的Promise没有调用resolve(),会一直阻塞 if (loading) { // 把resolve存入数组,待请求返回后执行resolve queue.push({resolve, reject}) } if (!loading && !localEnv) { loading = true console.log('questing env......') setTimeout(() => { localEnv = { platform: '141001', appid: 'aoshdakhpa8fkdng' } loading = false resolve(localEnv) // 异步请求结束,调用所有正在阻塞的Promise的resolve函数,返回结果,解除阻塞 while (p = queue.shift()) { p.resolve(localEnv) } }, 2000) } }) }

在这里插入图片描述

结语

利用好Promise没有resolve/reject会一直阻塞的特性,可以实现类似Java的wait/notify功能,实现同一时间多次异步请求函数都取到返回值,只触发一次异步请求的功能。



【本文地址】

公司简介

联系我们

今日新闻

    推荐新闻

    专题文章
      CopyRight 2018-2019 实验室设备网 版权所有