美文网首页程序员
ES6 生成器Generator

ES6 生成器Generator

作者: 袁某某 | 来源:发表于2017-03-13 10:48 被阅读41次

    生成器

    生成器(Generators): 一个更好的方法来构建遍历器。 --- 生成器和迭代器

    生成器就是一类特殊的函数,特殊之处在于:

    • 字面量(函数声明/函数表达式)的关键字function后面多了一个*,而且这个*前后允许有空白字符,如:
      function* foo(){}
      function *foo(){}
      function*foo(){}
    
    • 函数体中多了yield运算符
    • 普通函数的执行模式是: 执行-结束, 生成器的执行模式是: 执行-暂停-结束

    yield语句

    yield语句是Generator函数内部可以暂停执行程序的语句,yield语句后面的值可以是各种数据类型,字符串,整数,布尔值等等都可以。

    看个小栗子:

      function *foo() {
          yield 1;
          yield 'hello';
          yield 'generator';
          return true;
      }
      let f1 = foo();
      f1.next();  // Object {value: 1, done: false}
      f1.next();  // Object {value: "hello", done: false}
      f1.next();  // Object {value: "generator", done: false}
      f1.next();  // Object {value: true, done: true}
      f1.next();  // Object {value: undefined, done: true}
    

    这个例子反映了生成器的基本用法,有以下几点值得注意:

    1. 在调用foo()时,函数体中的逻辑并不会执行(控制台没有输出),直接调用f1.next()时才会执行
    2. f1是一个对象,它由生成器foo()调用而来,注意foo()并没有返回f1对象
    3. 调用f1.next()时,函数体中的逻辑才开始真正执行,每次调用时会到yield语句结束,并将yield的运算数作为结果返回
    4. f1.next()返回的结果是一个对象,对yield的运算数做了包装,并带上了done属性
    5. 当done属性为false时,表示该函数逻辑还未执行完,可以调用f1.next()继续执行
    6. 当返回的结果为return语句返回的结果,且done值为true
    7. 返回值中done为true时,仍然可以继续调用,返回的值为undefined

    yield和return

    看个栗子:

    function *bar() {
        yield 1;
        yield 'hello';
        return true;
        yield 'generator';
    }
    let b1 = bar();
    b1.next();  // Object {value: 1, done: false}
    b1.next();  // Object {value: "hello", done: false}
    b1.next();  // Object {value: true, done: true}
    b1.next();  // Object {value: undefined, done: true}
    

    从上面例子可以看出,当碰到return语句时,返回对象的done属性值就为true,遍历结束,不管后面是否还有yield或者return语句。不管是普通函数还是Generator函数,一旦遇到return语句,便不再返回新的值。

    yield 和 yield*

    在生成器中,yield* 可以把需要 yield 的值委托给另外一个生成器或者其他任意的可迭代对象。

    function* gen1() {
      yield 2;
      yield 3;
      yield 4;
    }
    
    function* gen2() {
      yield 1;
      yield* gen1();
      yield 5;
    }
    
    var g = gen2();
    
    g.next(); // Object { value: 1, done: false }
    g.next(); // Object { value: 2, done: false }
    g.next(); // Object { value: 3, done: false }
    g.next(); // Object { value: 4, done: false }
    g.next(); // Object { value: 5, done: false }
    g.next(); // Object { value: undefined, done: true }
    

    相关文章

      网友评论

        本文标题:ES6 生成器Generator

        本文链接:https://www.haomeiwen.com/subject/qhsfnttx.html