前言
众所周知,es6中有一个没人用的新特性,yield+Generator
最近在学习
File System Acess API
的时候在官方文档中看到了function* 的异步写法,从来没有用过这种写法,去
MDN
学习了一下
使用方式
废话不多说,直接上代码
function* test(x){
yield x
y = yield 2
yield fun(y)
}
function fun(x){
return x
}
let a = test(11)
a.next() // {value: 11, done: false}
a.next() // {value: 2, done: false}
a.next(333) // {value: 2, done: false} 结束了
a.next() // {value: undefined, done: true}
a.next() // {value: undefined, done: true}
a.next(123) // {value: undefined, done: true}
a.next(()=>{}) // {value: undefined, done: true}
a.next('asd') // {value: undefined, done: true}
一步一步看
我们通过function* 这种声明方式定义了一个生成器函数,返回一个Generator对象并赋值给a
当我们第一次调用a.next()时,执行了yield x,其实也就是相当于return,返回了{value: 11, done: false}
当我们第二次调用a.next()时,执行了yield 2,返回了{value: 2, done: false}
当我们第三次调用a.next(333)时,执行了y=333和yield fun(y),所以返回了{value: 2, done: false}
如果我们再调用a.next(),因为已经没有yield了,所以不管我们怎么调用,都是返回{value: undefined, done: true}
当然,这是最简单的用法,还有些高端(
让人看不懂的
)玩法,就不在此介绍了(
我也不会
)
使用场景
这玩意好像真的没什么大用…
而且写复杂了非常有可能让后续维护这段代码的人看不懂
我想了想,想到一个可能能用到的场景
比方说现在有一个步骤条,通过一次一次的点击依次调用fun1,fun2,fun3方法
正常来说,我们会在state里增加一个参数,去维护一个step,根据step来调用方法
但是我们也可以使用yield来实现
function* doStep(){
yield fun1()
yield fun2()
yield fun3()
}
const myGenerator = doStep()
<Bottom onClick={()=>{myGenerator.next()}}>
总结
不推荐使用,除非你真的想用