1.Generator是ES6中新增的语法,和Promise一样,都可以用来异步编程。
2.Generator函数和普通函数的区别:
(1)普通函数:一旦执行,就会从头走到尾,不会终止。
function normalFn(){
console.log('start')
console.log('middle')
console.log('end')
}
normalFn()
(2)Generator函数
[1]Generator不是一个函数,定义generator时,使用function*,使用yield来返回结果。
[2]调用Generator之后,它内部的代码不会立即执行,而是处于一个暂停的状态,并生成一个generator对象
[3]遇到yield时,会执行yield后面的表达式,并返回执行后的值,然后再次进入暂停阶段,此时done:false
[4]Generator返回的是一个iteration对象,因此可以使用next方法、for...of。
注意:iteration对象是一个指针对象,遍历器对象,有两种方法:
方法一:next():返回的格式为:{value:xx,done:xx}
方法二:使用for...of遍历,每次遍历得到value值。
[5]例子:
function* gen(){
console.log('start')
yield
console.log('middle')
yield
console.log('end')
}
let g = gen() //返回一个枚举器
g.next() //输出start
g.next() //输出middle
g.next() //输出end
分析:每次调用next方法,gen函数里的代码就会往下走一步,每次走到一个yield就停止执行。generator内部通过yield关键字,将代码中断,除非调用next(),否则generator函数不会继续往下执行。
3.yield关键字
generator方法返回一个枚举器,每次调用next(),在碰到yield的时候会停止运行,执行yield后面的表达式,并返回。
function* gen(){
console.log('start')
yield 'hello'
console.log('middle')
yield 'world'
console.log('end')
}
let g = gen()
console.log(g.next()) //{value:'hello',done:'false'}
console.log(g.next()) //{value:'world',done:'false'}
console.log(g.next()) //{value:undefined,done:'true'}
分析:next()会返回一个对象,对象的value属性就是yield后面的表达式的值。yield关键字将generator中断,并返回yield后面的表达式的值,赋值给next(){value:属性 },并等待下一次的next()
4.return关键字
(1)在generator中,如果有n个yield,我们就需要手动调用n+1次next()才能得到done:true的结果,但是最后一次的返回对象中的value:undefined。我们可以使用return关键字告知generator迭代结束,并将return返回的值给最后一个next()返回对象的value属性。
(2)例子:
function* gen(){
console.log('start')
yield 'hello world'
console.log('middle')
yield '!!!'
console.log('end')
return 'over'
}
let g = gen();
console.log(g.next()) //{value:'hello world',done:false}
console.log(g.next()) //{value:'!!!',done:false}
console.log(g.next()) //{value:'over',done:true}
(3)return关键字有两个作用
[1]告知generator迭代的结果
[2]把return的值给最后一个迭代返回对象的value属性