诸暨网站制作设计/千度搜索引擎

诸暨网站制作设计,千度搜索引擎,重庆住房建设部网站,国外跨境电商b2b平台有哪些闭包讲解 ES6回顾:闭包->(优点:实现工厂函数、记忆化和异步实现)、(应用场景:Promise的then与catch的回调、async/await、柯里化函数) 以下是与 JavaScript 闭包相关的常见考点整理,结合 Pro…

闭包讲解

ES6回顾:闭包->(优点:实现工厂函数、记忆化和异步实现)、(应用场景:Promise的then与catch的回调、async/await、柯里化函数)

以下是与 JavaScript 闭包相关的常见考点整理,结合 Promise、async/await、缓存结果、工厂函数、柯里化等内容,并依据我搜索到的资料进行详细说明:


1. 闭包(Closure)

  • 定义:由函数及其引用的外部词法环境变量组成,即使外部函数执行完毕,内部函数仍能访问这些变量 。
  • 作用
    • 延长外部函数变量的生命周期,使外部可操作内部数据(如模块化封装)。
    • 避免全局变量污染,实现私有变量 。
  • 缺点:不当使用会导致内存泄漏(变量无法被回收)。
  • 应用场景
    • 缓存结果:通过闭包保存计算结果,避免重复计算(记忆化函数)。
    • 工厂函数:生成带有特定配置的函数实例(如计数器生成器)。
    • 柯里化:拆分多参数函数为链式单参数调用,依赖闭包保存中间参数 。
    • 异步回调:在事件处理或定时器中保留上下文 。

2. Promise

  • 核心概念
    • 三种状态:pendingfulfilledrejected,状态一旦改变不可逆 。
    • 解决回调地狱(Callback Hell),支持链式调用 .then().catch()
  • 常用方法
    • Promise.all():所有 Promise 成功时返回结果数组,任一失败立即拒绝 。
    • Promise.race():首个完成的 Promise 决定最终状态 。
    • Promise.resolve()/Promise.reject():快速创建成功/失败的 Promise 。
  • 手写实现:常考手写 Promise.allPromise.race 的实现 。

3. async/await

  • 本质:基于 Generator 和 Promise 的语法糖,使异步代码更接近同步写法 。
  • 规则
    • async 函数返回 Promise 对象,return 值会被 Promise.resolve() 包装 。
    • await 后接 Promise,暂停当前函数执行直到 Promise 完成(属于微任务)。
    • await 只能在 async 函数内使用,否则需通过立即调用异步函数(如 (async () => { ... })())。
  • 错误处理:用 try...catch 捕获 await 后的 Promise 拒绝 。
  • 执行顺序await 后的代码相当于放入 .then() 中,属于微任务队列 。
function asyncToGenerator(fn) {// 返回函数return function() {const gen = fn.apply(this, arguments);//生成器// 方法返回一个Promise对象return new Promise((resolve, reject) => {function step(key, arg) {// console.log(arg)let result;try {result = gen[key](arg);//生成器返回数据{value,done:bool}// 移除调试日志以保持输出整洁} catch (error) {return reject(error);}//如果执行器执行完成if (result.done) {return resolve(result.value);}//如果执行器未完成,将当前结果传入Promise的resolve方法中,并递归调用step方法Promise.resolve(result.value).then(v => step("next", v),e => step("throw", e));}step("next");});};
}// 使用示例(已修复)
const asyncFunction = asyncToGenerator(function* () {// 修正 Promise 的创建方式,使用箭头函数包裹 resolveconst result = yield new Promise(resolve => setTimeout(() => resolve("result"), 1000));const result1 = yield new Promise(resolve => setTimeout(() => resolve("result2"), 2000));console.log(result, result1); // 输出: "result" "result2"(3秒后)
});asyncFunction(); // 启动执行

4. 柯里化(Currying)

  • 定义:将多参数函数转换为一系列单参数函数链式调用的技术,依赖闭包保存中间参数 。
  • 示例
  function add(x) {return function(y) {return x + y;};}add(2)(3); // 5
  • 应用:参数复用、延迟执行、函数组合 。

5. 工厂函数

  • 作用:通过闭包生成具有独立状态的函数实例。例如生成独立的计数器:
  function createCounter() {let count = 0;return function() {return ++count;};}const counter1 = createCounter(); // 独立作用域
  • 场景:封装私有变量、实现模块化 。

6. 闭包与异步编程的结合

  • 事件回调:在闭包中使用 async/await 处理异步逻辑,避免全局变量污染 。
  button.addEventListener('click', () => {(async () => {const data = await fetchData();console.log(data);})();});
  • 定时器:闭包保存定时器状态,结合 async/await 控制执行流程 。

7. 内存管理

  • 内存泄漏:闭包长期引用外部变量会导致内存无法释放,需及时解除引用(如手动置 null)。
  • 优化:避免不必要的闭包,或在不需要时清除事件监听器、定时器等 。

总结

闭包是 JavaScript 的核心概念,与异步编程(Promise/async/await)、函数式编程(柯里化、工厂函数)紧密相关。理解闭包的作用域机制、内存管理,以及与其他特性的结合方式,是应对面试和实际开发的关键。


async/await 底层实现解析

async/await 是 JavaScript 中处理异步操作的语法糖,其底层实现基于 PromiseGenerator(生成器) 的协同机制。通过分析资料中的代码转换、设计原理和规范定义,其核心实现逻辑可拆解如下:


一、核心依赖:Promise 与 Generator 的协作
  1. Promise 的基础作用
    async/await 的异步控制完全依赖于 Promise 的链式调用。每个 await 表达式本质上会创建一个 Promise,并将后续代码包装到 .then() 中等待执行。例如:

    async function foo() {const result = await somePromise; // 等价于 somePromise.then(result => {...})
    }
    

    这种设计使得异步操作的 状态管理错误传播 能够通过 Promise 链式结构实现。

  2. Generator 的流程控制
    Generator 函数通过 yield 关键字暂停执行,并通过迭代器(Iterator)手动恢复。async/await 利用这一特性,将异步代码的 暂停-恢复机制 转化为生成器函数的 yield 操作。例如,以下代码:

    async function a() {const res = await asyncTask();
    }
    

    会被 Babel 转换为使用 Generator 的代码:

    function a() {return __awaiter(this, void 0, void 0, function* () {const res = yield asyncTask();});
    }
    

    这里的 yield 替代了 await,而 __awaiter 函数负责管理生成器的迭代。


二、转换逻辑:代码降级与执行器封装

通过 Babel/TypeScript 等工具的代码转换,async/await 的实现可拆解为以下步骤:

  1. 生成器函数包装
    async 函数被转换为生成器函数,await 被替换为 yield。例如:

    // 原始代码
    async function fetchData() {const data = await fetch(url);return data;
    }// 转换后代码(简化)
    function fetchData() {return __awaiter(this, function* () {const data = yield fetch(url);return data;});
    }
    
  2. 执行器函数(如 __awaiter)的作用
    执行器负责驱动生成器的迭代,并处理 Promise 的链式调用。其核心逻辑如下:

    • 将生成器的每个 yield 值包装为 Promise。
    • 通过 generator.next(value) 将 Promise 的结果传递回生成器。
    • 捕获错误并通过 generator.throw(error) 抛出异常。
    function __awaiter(generator) {return new Promise((resolve, reject) => {function step(result) {if (result.done) {resolve(result.value);} else {Promise.resolve(result.value).then(value => step(generator.next(value)), // 传递结果并继续迭代error => step(generator.throw(error)) // 抛出错误);}}step(generator.next());});
    }
    

    此过程实现了 自动迭代错误冒泡,使代码看似同步执行。


三、执行顺序与事件循环的关联
  1. 微任务队列的调度
    await 后的代码会被包装为微任务(Microtask),在 Promise 解决后加入微任务队列。例如:

    async function demo() {console.log(1);await Promise.resolve();console.log(2); // 相当于 Promise.resolve().then(() => console.log(2))
    }
    demo();
    console.log(3);
    // 输出顺序:1 → 3 → 2
    

    这种机制确保了异步代码的执行不会阻塞主线程。

  2. 协程(Coroutine)模型的实现
    async/await 通过生成器和 Promise 模拟了协程的 挂起-恢复 行为:

    • 挂起:在 await 处暂停生成器,释放主线程。
    • 恢复:当 Promise 解决后,通过执行器继续生成器的迭代。

四、错误处理机制的实现
  1. try/catch 的转换
    async 函数中的 try/catch 会被转换为 Promise 的 .catch() 链。例如:

    async function foo() {try {await somePromise();} catch (err) {handleError(err);}
    }
    

    转换后逻辑:

    function* foo() {try {const result = yield somePromise();} catch (err) {handleError(err);}
    }
    

    执行器在生成器抛出错误时触发 reject

  2. 未捕获异常的传播
    若未使用 try/catch,错误会通过 Promise 链冒泡到顶层,触发 unhandledrejection 事件。


五、性能与优化考量
  1. 生成器与 Promise 的开销
    async/await 相比原生 Promise 链会引入额外开销(如生成器对象的创建),但在现代引擎中差异可忽略。

  2. 并发的实现方式
    需显式使用 Promise.all() 实现并行,避免顺序等待:

    async function parallel() {const [a, b] = await Promise.all([task1(), task2()]); // 并行执行
    }
    

    若直接顺序 await,会导致任务串行执行。


总结:async/await 的架构设计

层级实现机制作用
语法层async/await 关键字提供同步代码风格的异步写法
转换层Babel/TypeScript 代码降级将 async/await 转为 Generator + Promise
运行时层生成器迭代器 + Promise 链管理暂停/恢复、错误传播
事件循环层微任务队列调度确保异步代码非阻塞执行

通过多层抽象,async/await 将复杂的异步流程控制简化为直观的同步式代码,同时保持与 Promise 的完全兼容性。

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mzph.cn/diannao/73288.shtml

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

OpenMCU(三):STM32F103 FreeRTOS移植

概述 本文主要描述了STM32F103移植FreeRTOS的简要步骤。移植描述过程中,忽略了Keil软件的部分使用技巧。默认读者熟练使用Keil软件。本文的描述是基于OpenMCU_RTOS这个工程,该工程已经下载放好了移植STM32F103 FreeRTOS的所有文件 OpenMCU_RTOS工程的愿景…

生成对抗网络(GAN)原理与应用

目录 一、引言 二、GAN的基本原理 (一)生成器(Generator)的工作机制 (二)判别器(Discriminator)的工作机制 (三)对抗训练的过程 三、GAN在AIGC生图中的应…

STM32 内置的通讯协议

数据是以帧为单位发的 USART和UART的区别就是有没有同步功能 同步是两端设备有时钟连接,异步是没时钟连接,靠约定号的频率(波特率)接收发送数据 RTS和CTS是用来给外界发送已“可接收”或“可发送”信号的,一般用不到…

Appium等待机制--强制等待、隐式等待、显式等待

书接上回,Appium高级操作--其他操作-CSDN博客文章浏览阅读182次,点赞6次,收藏7次。书接上回Appium高级操作--从源码角度解析--模拟复杂手势操作-CSDN博客。https://blog.csdn.net/fantasy_4/article/details/146162851主要讲解了Appium的一些…

NFS实验配置笔记

NFS NFS服务 nfs,最早是Sun这家公司所发展出来的,它最大的功能就是可以透过网络,让不同的机器,不同的操作系统,进行实现文档的共享。所以你可以简单的将他看做是文件服务器。 实验准备 ①先准备一个服务器端的操作…

深度学习|MAE技术全景图:自监督学习的“掩码魔法“如何重塑AI基础

一、引言:深度学习的困境与自监督的曙光 深度学习(Deep Learning)无疑是当今人工智能领域基础中的基础。从图像识别到自然语言处理(NLP),它在无数任务中展现了卓越性能。例如,在安防监控中&…

【SpringBoot】实现登录功能

在上一篇博客中,我们讲解了注册页面的实现。在此基础上会跳转到登录页面,今天给大家带来的是使用 SpringBoot,MyBatis,Html,CSS,JavaScript,前后端交互实现一个登录功能。 目录 一、效果 二、…

mingw工具源码编译

ming-w64 mingw编译生成的库,需要mingw的lib文件支持。 https://github.com/mingw-w64/mingw-w64 使用msys2的bash git checkout v8.0.3 ./configure --disable-dependency-tracking --targetx86_64-w64-mingw32 mingw32-make.exe -j4 修改makefile中的make 改成mi…

LSTM方法实践——基于LSTM的汽车销量时序建模与预测分析

Hi,大家好,我是半亩花海。本实验基于汽车销量时序数据,使用LSTM网络(长短期记忆网络)构建时间序列预测模型。通过数据预处理、模型训练与评估等完整流程,验证LSTM在短期时序预测中的有效性。 目录 一、实验…

Stable Diffusion教程|快速入门SD绘画原理与安装

什么是Stable Diffusion,什么是炼丹师?根据市场研究机构预测,到2025年全球AI绘画市场规模将达到100亿美元,其中Stable Diffusion(简称SD)作为一种先进的图像生成技术之一,市场份额也在不断增长&…

Webpack构建流程详解优化前端性能\Dev-Server与Proxy\网络攻击\HMR

简版 核心流程图 根据,Webpack的构建流程分为初始化、编译和输出三个阶段。初始化阶段读取配置、加载插件、实例化Compiler。编译阶段(构建依赖关系)涉及Compiler类的运行,生成Compilation对象,处理模块依赖。输出阶…

零成本搭建Calibre个人数字图书馆支持EPUB MOBI格式远程直读

文章目录 前言1.网络书库软件下载安装2.网络书库服务器设置3.内网穿透工具设置4.公网使用kindle访问内网私人书库 前言 嘿,各位书虫们!今天要给大家安利一个超级炫酷的技能——如何在本地Windows电脑上搭建自己的私人云端书库。亚马逊服务停了&#xff…

【Linux 指北】常用 Linux 指令汇总

第一章、常用基本指令 # 注意: # #表示管理员 # $表示普通用户 [rootlocalhost Practice]# 说明此处表示管理员01. ls 指令 语法: ls [选项][目录或文件] 功能:对于目录,该命令列出该目录下的所有子目录与文件。对于文件&#xf…

跟踪napi_gro_receive_entry时IP头信息缺失的分析

问题描述 在使用eBPF程序跟踪napi_gro_receive_entry内核跟踪点时,发现获取到的IP头部字段(如saddr、daddr、protocol)为空值。 代码如下: /* 自定义结构体来映射 napi_gro_receive_entry tracepoint 的 format */ struct napi…

Android子线程更新View的方法原理

对于所有的Android开发者来说,“View的更新必须在UI线程中进行”是一项最基本常识。 如果不在UI线程中更新View,系统会抛出CalledFromWrongThreadException异常。那么有没有什么办法可以不在UI线程中更新View?答案当然是有的! 一…

【Manus资料合集】激活码内测渠道+《Manus Al:Agent应用的ChatGPT时刻》(附资源)

DeepSeek 之后,又一个AI沸腾,冲击的不仅仅是通用大模型。 ——全球首款通用AI Agent的破圈启示录 2025年3月6日凌晨,全球AI圈被一款名为Manus的产品彻底点燃。由Monica团队(隶属中国夜莺科技)推出的“全球首款通用AI…

Python----计算机视觉处理(opencv:像素,RGB颜色,图像的存储,opencv安装,代码展示)

一、计算机眼中的图像 像素 像素是图像的基本单元,每个像素存储着图像的颜色、亮度和其他特征。一系列像素组合到一起就形成 了完整的图像,在计算机中,图像以像素的形式存在并采用二进制格式进行存储。根据图像的颜色不 同,每个像…

SQLiteStudio:一款免费跨平台的SQLite管理工具

SQLiteStudio 是一款专门用于管理和操作 SQLite 数据库的免费工具。它提供直观的图形化界面,简化了数据库的创建、编辑、查询和维护,适合数据库开发者和数据分析师使用。 功能特性 SQLiteStudio 提供的主要功能包括: 免费开源,可…

【软考网工-实践篇】DHCP 动态主机配置协议

一、DHCP简介 DHCP,Dynamic Host Configuration Protocol,动态主机配置协议。 位置:DHCP常见运行于路由器上,作为DHCP服务器功能:用于自动分配IP地址及其他网络参数给网络中的设备作用:简化网络管理&…

【Linux学习笔记】Linux用户和文件权限的深度剖析

【Linux学习笔记】Linux用户和文件权限的深度剖析 🔥个人主页:大白的编程日记 🔥专栏:Linux学习笔记 前言 文章目录 【Linux学习笔记】Linux用户和文件权限的深度剖析前言一. Linux权限管理1.1 文件访问者的分类(人)…