讲师中心 微信公众号
AI工具推荐 视频效率加速

javascript生成器函数如何工作?_学习javascript生成器与迭代器【教程】

小涛吖_6261

小涛吖_6261

发布时间:2026-01-28 14:17:02

|

735人浏览过

|

来源于php中文网

原创

JavaScript生成器函数是可暂停执行的函数,返回迭代器对象;调用后需用next()推进执行,yield暂停并输出值,return终止并设done: true。

javascript生成器函数如何工作?_学习javascript生成器与迭代器【教程】

JavaScript 生成器函数不是“异步函数的简化写法”,它本质是**可暂停执行的函数,返回一个迭代器对象**。你调用它不会立即运行函数体,而是得到一个 Generator 实例,只有调用它的 next() 方法时,才从头或上次暂停处继续执行,直到遇到下一个 yield 或函数结束。

生成器函数定义与基本调用:必须用 function* 语法

生成器函数声明必须带星号(function*),这是硬性语法要求;箭头函数不支持生成器。调用后返回的是一个迭代器对象,不是普通函数返回值:

function* count() {
  yield 1;
  yield 2;
  return 3;
}
const gen = count(); // 不执行函数体,只返回 Generator 对象
console.log(gen.next()); // { value: 1, done: false }
console.log(gen.next()); // { value: 2, done: false }
console.log(gen.next()); // { value: 3, done: true }
  • yield 暂停并输出值,return 终止并设 done: true
  • 多次调用 next() 是推进执行的关键,不是“重跑函数”
  • 如果生成器已 done: true,后续 next() 仍返回 { value: undefined, done: true }

yield 可接收外部传入值:双向通信机制

yield 表达式本身是有返回值的——它等于下一次调用 next(arg) 时传入的参数。这是生成器实现协程式控制流的基础:

function* echo() {
  const a = yield 'first';
  console.log('a:', a); // a: 'hello'
  const b = yield 'second';
  console.log('b:', b); // b: 'world'
}
const it = echo();
console.log(it.next());      // { value: 'first', done: false }
console.log(it.next('hello')); // { value: 'second', done: false }
console.log(it.next('world')); // { value: undefined, done: true }
  • 首次 next() 总是忽略传参,只启动执行到第一个 yield
  • 后续 next(x) 中的 x 成为上一个 yield 表达式的值
  • 这个特性常被用于手写 co 类库、模拟 async/await 的早期实现

生成器与 for...of 和扩展运算符配合:自动消费迭代器

生成器对象实现了 Symbol.iterator,因此天然支持 for...of、[...gen]、Array.from(gen) 等语法,但注意:它们**只会遍历 yield 的值,忽略 return 的终值**:

Java Maven Common
Java Maven Common

Java Maven 项目审查工作流的通用输入处理。当 Java Maven 项目以 ZIP压缩包或 GitLab 仓库 URL 形式提供且需要...时使用。

下载

立即学习“Java免费学习笔记(深入)”;

function* nums() {
  yield 1;
  yield 2;
  return 999; // 这个 999 不会被 for...of 捕获
}
for (const n of nums()) {
  console.log(n); // 输出 1, 2 —— 不会输出 999
}
console.log([...nums()]); // [1, 2]
  • for...of 内部反复调用 next() 直到 done: true,但只收集 value 字段
  • 若需捕获 return 值,必须手动调用 next() 并检查 done
  • 生成器一旦 done,无法重置;如需重复使用,得重新调用生成器函数创建新实例

常见误用:把生成器当 Promise 用,或混淆 yield 与 await

生成器本身不处理异步,yield 后跟 Promise 不会自动等待;要实现类似 async/await,必须配合同步驱动器(如 co 库或手写 runner):

function* fetchUser() {
  const res = yield fetch('/api/user'); // ❌ 这里 res 是 Promise 实例,不是响应结果
  return res.json();
}
// 必须用 runner 包装才能真正 await:
function run(genFn) {
  const it = genFn();
  function next(val) {
    const { value, done } = it.next(val);
    if (done) return value;
    return value.then(res => next(res)); // 手动 resolve Promise 并递归 next
  }
  return next();
}
  • 直接 yield Promise 没有意义,JS 引擎不会自动 await 它
  • 现代代码应优先用 async/await,生成器主要用于底层抽象(如 redux-saga)、状态机或需要精细控制执行节奏的场景
  • 调试时注意:生成器函数在 DevTools 中断点可能跳转不直观,因实际执行分散在多次 next() 调用中

生成器的核心价值不在“写起来多简洁”,而在于它把函数执行权交还给调用方——你可以决定何时推进、传什么数据、甚至中途注入异常(it.throw(err))。这种控制反转正是它难以被替代的地方,也是最容易被忽略的复杂性所在。

相关文章

java速学教程(入门到精通)
java速学教程(入门到精通)

java怎么学习?java怎么入门?java在哪学?java怎么学才快?不用担心,这里为大家提供了java速学教程(入门到精通),有需要的小伙伴保存下载就能学习啦!

下载

相关标签:

本站声明:本文内容由网友自发贡献,版权归原作者所有,本站不承担相应法律责任。如您发现有涉嫌抄袭侵权的内容,请联系admin@php.cn

热门AI工具

更多
DeepSeek

DeepSeek是一款面向对话、写作、编程和推理场景的AI大模型工具。

豆包大模型

豆包大模型是一款由字节跳动推出的企业级大语言模型服务平台。

AionClaw
AionClaw Hot

AionClaw是一款面向办公、创作和编程任务的AI桌面智能体。

蛙蛙写作

一款AI论文写作工具,主要用于超级AI智能写作助手,适合需要提升相关任务效率的用户。

UP简历
UP简历 Hot

一款AI办公效率工具,主要用于基于AI技术的免费在线简历制作工具,适合需要提升相关任务效率的用户。

VibeKnow
VibeKnow Hot

一款AI视频创作工具,主要用于全球首个AI知识视频创作平台,文档、文章、网页,一键生成视频,适合需要提升相关任务效率的用户。

Loomy
Loomy Hot

一款AI工具,主要用于科大讯飞发布的桌面级 AI 助理,比 OpenClaw 更易用、更安全!,适合需要提升相关任务效率的用户。

墨刀AI
墨刀AI Hot

一款AI图像与设计工具,主要用于产品经理的专属智能体,适合需要提升相关任务效率的用户。

WorkBuddy

一款AI办公效率工具,主要用于腾讯云推出的AI原生桌面智能体工作台,适合需要提升相关任务效率的用户。

相关专题

更多
java基础知识汇总
java基础知识汇总

java基础知识有Java的历史和特点、Java的开发环境、Java的基本数据类型、变量和常量、运算符和表达式、控制语句、数组和字符串等等知识点。想要知道更多关于java基础知识的朋友,请阅读本专题下面的的有关文章,欢迎大家来php中文网学习。

6044

2023.10.24

Go语言中的运算符有哪些
Go语言中的运算符有哪些

Go语言中的运算符有:1、加法运算符;2、减法运算符;3、乘法运算符;4、除法运算符;5、取余运算符;6、比较运算符;7、位运算符;8、按位与运算符;9、按位或运算符;10、按位异或运算符等等。本专题为大家提供相关的文章、下载、课程内容,供大家免费下载体验。

2884

2024.02.23

php三元运算符用法
php三元运算符用法

本专题整合了php三元运算符相关教程,阅读专题下面的文章了解更多详细内容。

1752

2025.10.17

js正则表达式
js正则表达式

php中文网为大家提供各种js正则表达式语法大全以及各种js正则表达式使用的方法,还有更多js正则表达式的相关文章、相关下载、相关课程,供大家免费下载体验。

4296

2023.06.20

js获取当前时间
js获取当前时间

JS全称JavaScript,是一种具有函数优先的轻量级,解释型或即时编译型的编程语言;它是一种属于网络的高级脚本语言,主要用于Web,常用来为网页添加各式各样的动态功能。js怎么获取当前时间呢?php中文网给大家带来了相关的教程以及文章,欢迎大家前来学习阅读。

1335

2023.07.28

js 字符串转数组
js 字符串转数组

js字符串转数组的方法:1、使用“split()”方法;2、使用“Array.from()”方法;3、使用for循环遍历;4、使用“Array.split()”方法。本专题为大家提供js字符串转数组的相关的文章、下载、课程内容,供大家免费下载体验。

1718

2023.08.03

js是什么意思
js是什么意思

JS是JavaScript的缩写,它是一种广泛应用于网页开发的脚本语言。JavaScript是一种解释性的、基于对象和事件驱动的编程语言,通常用于为网页增加交互性和动态性。它可以在网页上实现复杂的功能和效果,如表单验证、页面元素操作、动画效果、数据交互等。

9843

2023.08.17

js删除节点的方法
js删除节点的方法

js删除节点的方法有:1、removeChild()方法,用于从父节点中移除指定的子节点,它需要两个参数,第一个参数是要删除的子节点,第二个参数是父节点;2、parentNode.removeChild()方法,可以直接通过父节点调用来删除子节点;3、remove()方法,可以直接删除节点,而无需指定父节点;4、innerHTML属性,用于删除节点的内容。

960

2023.09.01

OpenJDK JVM参数怎么调优
OpenJDK JVM参数怎么调优

Java应用运行缓慢,如何调整JVM参数?本专题介绍OpenJDK JVM性能调优的基本流程,涵盖性能指标确认、运行数据采集、内存配置和垃圾回收分析,帮助你先定位瓶颈,再通过对照测试验证效果,避免直接套用参数而影响应用稳定性。

20

2026.10.16

热门下载

更多
网站特效
/
网站源码
/
网站素材
/
前端模板

精品课程

更多
相关推荐
/
热门推荐
/
最新课程
WebStorm 官方调试文档
WebStorm 官方调试文档

共0课时 | 0人学习

React 教程
React 教程

共58课时 | 12.2万人学习

TypeScript 教程
TypeScript 教程

共19课时 | 6.7万人学习

关于我们 免责申明 举报中心 意见反馈 讲师合作 广告合作 最新更新
php中文网:公益在线php培训,帮助PHP学习者快速成长!
关注服务号
PHP中文网订阅号
每天精选资源文章推送

Copyright 2014-2026 https://www.php.cn/ All Rights Reserved | php.cn