??????C#??TypeScript - Generator
???????????Promise??Promise????????????????then???????callback???Щ?????????????????ES6???????Generator????????????????????????Promise???????????????ES7?鰸?е?async await??
???????async await???????????Generator??????????Generator???????
???????????????????Generator.
????Generator??
?????????????????
function* getAsync(id: string){
yield 'id';
yield id;
return 'finish';
}
let p = getAsync('123');
console.info(p.next());
console.info(p.next());
console.info(p.next());
????????o??????????????function??????????*???????function*?????????????yield???????????????C#??У??????????????????????
??????ES6??yield????????????????????????????????????next()???????з???????????????
??????????????????????£?
????{ value: 'id'?? done: false }
????{ value: '123'?? done: false }
????{ value: 'finish'?? done: true }
???????????next()?????????????value???yield??????done???????????????
?????????????return??finish?done???true?????????????????next()?????????{ value: undefined?? done: true }.
????Generator???????
????Generator?????ES6??Э???????????????????й?????????????????????????е?????????????????????????????????????????????????к????????????
??????νЭ????????????????????С????е?λ????????????ж??Э???Э???????????????????????????????????????????Э??????С?
?????????????????????????Э????????????????????????Э???????????
????????JavaScript???????????????????????????????????????????Э??????????????Э?????? 1:N??
????????????Э??goroutine??go?????????? M:N?????Э?????????Э?????????
??????Generator??????yield????????к????????????next()????????????沿???
??????????????Generator?????????????????????????е??????????????????????????????????for...of????????????????????done?true??????
function* getAsync(id: string){
yield 'id';
yield id;
return 'finish';
}
let p = getAsync('123');
for(let id of p){
console.info(id);
}
??????????????
????id
????123
????????????finish??done??true??????for...of?????????????????????????
????????Generator??next()?????????????
function* calc(num: number){
let count = yield 1 + num;
return count + 1;
}
let p = calc(2);
console.info(p.next().value); // 3
console.info(p.next().value); // NaN
//console.info(p.next(3).value); // 4
?????????????????????yield 1 + num??????yield 1????1?????????????2???????3.
??????????????????????????????????3??????????yield 1??????????????????????????yield??????????undefined??
????????yield 1????undefined??undefined + num???????NaN??count + 1?????NaN???????????NaN??
????????????????????????????????????????????????ε???3??next(3)????????????????????????
???????????ε??????У?????????η???????????
let curr = p.next();
while(!curr.done){
console.info(curr.value);
curr = p.next(curr.value);
}
console.info(curr.value); // ????
Generator???????Promise???????????????????
function delay(): Promise<void>{
return new Promise<void>((resolve?? reject)=>{setTimeout(()=>resolve()?? 2000)});
}
function* run(){
console.info('start');
yield delay();
console.info('finish');
}
let generator = run();
generator.next().value.then(()=>generator.next());
????run?????????????????????????????????????'start'?????2???????'finish'??
??????????????????????then??????TJ????д??CO??飬??????????????????????Generator????????co???ɡ?
????co(run).then(()=>console.info('success'));
????co????????????????????????
function co(gen) {
var ctx = this;
var args = slice.call(arguments?? 1);
return new Promise(function(resolve?? reject) {
if (typeof gen === 'function') gen = gen.apply(ctx?? args);
if (!gen || typeof gen.next !== 'function') return resolve(gen);
onFulfilled(); //????????????????????next()??then()
function onFulfilled(res) {
var ret;
try {
ret = gen.next(res); // next()?? res??????????
} catch (e) {
return reject(e);
}
next(ret); // ???????then??????ε???onFulfilled()?????
return null;
}
function onRejected(err) { // ???????????
var ret;
try {
ret = gen.throw(err);
} catch (e) {
return reject(e);
}
next(ret);
}
function next(ret) {
if (ret.done) return resolve(ret.value); // done??true?????????????????
var value = toPromise.call(ctx?? ret.value);
if (value && isPromise(value)) return value.then(onFulfilled?? onRejected); //???onFulfilled
return onRejected(new TypeError('You may only yield a function?? promise?? generator?? array?? or object?? '
+ 'but the following object was passed: "' + String(ret.value) + '"'));
}
});
}
???????????co???????????????д???????Generator?????????????????????????????Promise?????done?true??
?????????co???????????????????????в??????????async await??????????????????????????????????