ES6学习Generator 函数(生成器)(八)

这里写目录标题

一、基本概念

  • Generator 函数是 ES6 提供的一种异步编程解决方案,语法行为与传统函数完全不同,Generator 函数有多种理解角度。
  • 语法上,首先可以把它理解成,Generator 函数是一个状态机,封装了多个内部状态。
    执行 Generator 函数会返回一个遍历器对象,也就是说,Generator 函数除了状态机,还是一个遍历器对象生成函数。返回的遍历器对象,可以依次遍历 Generator 函数内部的每一个状态。
  • 形式上,Generator函数是一个普通函数,但是有两个特征。一是, function 关键字与函数名之间有一个星号;二是,函数体内部使用 yield 表达式,定义不同的内部状态( yield 在英语里的意思就是"产出")。
  • 由于 Generator 函数返回的遍历器对象,只有调用 next 方法才会遍历下一个内部状态,所以其实提供了一种可以暂停执行的函数。yield表达式就是暂停标志。

二、代码

js 复制代码
        //生成器函数:function关键字和函数名之间有一个*
        function* add(){
            console.log('start');
            let x = yield '2';
            console.log('one:'+2);
            let y = yield '3';
            console.log('two:'+y);
            return x+y;

        }
        // 返回一个遍历器对象
        let fn=add();
        // next() 恢复执行标志
        console.log(fn.next());
        // 当 next() 传入参数时,该参数就会被当作上一个 yield 表达式的返回值 ,即 x = 20, y = 3
        console.log(fn.next(20));// one:20     {value: '3', done: false}
        console.log(fn.next(30));// two:30     {value: '50', done: true}
  • 使用场景:为不具备 Iterator 接口的对象提供了遍历操作
  • 利用for...of循环,可以写出遍历任意对象(object)的方法。原生的 JavaScript 对象没有遍历接口(不具备 Symbol.iterator方法),无法使用for...of循环,通过 Generator 函数为它加上这个接口,即将 Generator 函数加到对象的Symbol.iterator属性上面,就可以用了。
js 复制代码
        //Gemerator 生成器函数
        function* objectEntries(obj) {
            //获取对象的所有key保存到数组
            const propKeys = Object.keys(obj);
            for (const propkey of propKeys) {
                yield [propkey, obj[propkey]]
            }

        }

        const obj = {
            book: 'ES6学习',
            price: 18
        }
        // 把 Generator 生成器函数赋值给对象的Symbol.iterator属性, 为该对象加上遍历器接口
        obj[Symbol.iterator] = objectEntries;
        console.log(obj);//{book: 'ES6学习', price: 18, Symbol(Symbol.iterator):
        // objectEntries(obj) 等价于 obj[Symbol.iterator](obj) 
        for (let [key, value] of objectEntries(obj)) {
            console.log(`${key}: $value`);
        }

三、Generator 函数的异步应用

Generator 函数在ajax请求的异步应用,让异步代码同步化

Generator 函数在加载页面的异步应用

js 复制代码
       //Generator 函数在加载页面的异步应用
       // 1.加载 Loading...页面
       // 2.数据加载完成...(异步操作)
       // 3.Loading 关闭掉
       function loadUI() {
           console.log('加载 Loading...页面');
       }

       function showData() {
           // 模拟数据加载异步操作
           setTimeout(() => {
               console.log('数据加载完成');
           }, 1000);
       }

       function hideUI() {
           console.log('隐藏 Loading...页面');
       }

       loadUI();
       showData();
       hideUI();

上述代码执行后效果:

复制代码
加载 Loading...页面
隐藏 Loading...页面
数据加载完成

实际需求是加载数据完成后才关闭页面,但由于三个函数函数是同步执行的,数据加载需要时间,在数据未加载完成时,就已经隐藏loading页面。通过 Generator 函数可以解决这个问题。

js 复制代码
         function* load(){
            loadUI();
            yield showData();     
            hideUI()
        }

        const itLoad = load();
        itLoad.next();

        function loadUI() {
            console.log('加载 Loading...页面');
        }

        function showData() {
            // 模拟数据加载异步操作
            setTimeout(() => {
                console.log('数据加载完成');
                itLoad.next();
            }, 1000);
        }

        function hideUI() {
            console.log('隐藏 Loading...页面');
        }

三级目录

相关推荐
None3218 分钟前
【NestJs】使用Winston+ELK分布式链路追踪日志采集
javascript·node.js
Qinana1 小时前
从代码到智能体:MCP 协议如何重塑 AI Agent 的边界
前端·javascript·mcp
Marshall1511 小时前
zzy-scroll-timer:一个跨框架的滚动定时器插件
前端·javascript
明月_清风3 小时前
打字机效果优化:用 requestAnimationFrame 缓冲高频文字更新
前端·javascript
明月_清风3 小时前
Markdown 预解析:别等全文完了再渲染,如何流式增量渲染代码块和公式?
前端·javascript
程序猿的程16 小时前
开源一个 React 股票 K 线图组件,传个股票代码就能画图
前端·javascript
大雨还洅下17 小时前
前端JS: 虚拟dom是什么? 原理? 优缺点?
javascript
唐叔在学习17 小时前
[前端特效] 左滑显示按钮的实现介绍
前端·javascript
青青家的小灰灰17 小时前
深入理解事件循环:异步编程的基石
前端·javascript·面试
前端Hardy18 小时前
HTML&CSS&JS:打造丝滑的3D彩纸飘落特效
前端·javascript·css