Created
January 11, 2014 21:24
-
-
Save dtao/8377077 to your computer and use it in GitHub Desktop.
An idea for how generators could be implemented pre-ES6
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
/** | |
* Using yield to create a generator -- only possible in ES6/Harmony. | |
*/ | |
function fibonacci(limit) { | |
var fn1 = 1; | |
var fn2 = 1; | |
while (1) { | |
var current = fn2; | |
fn2 = fn1; | |
fn1 = fn1 + current; | |
if (limit && current > limit) | |
return; | |
yield current; | |
} | |
} | |
/** | |
* This should be possible in pre-ES6 versions of ECMAScript. | |
*/ | |
var fibonacci = createGenerator(function(limit, yield) { | |
var fn1 = 1; | |
var fn2 = 1; | |
while (1) { | |
var current = fn2; | |
fn2 = fn1; | |
fn1 = fn1 + current; | |
if (limit && current > limit) | |
return; | |
yield(current); | |
} | |
}); | |
/** | |
* How would it work? | |
* | |
* - generator uses a JS parser (e.g., esprima, acorn) to parse the source of | |
* the function passed to it using Function.prototype.toString. | |
* | |
* - all possible loops (for, while, do/while) are translated in the AST to | |
* async-friendly forms accepting callbacks. | |
* | |
* for example: | |
* while (1) { [code] } | |
* | |
* would become: | |
* library.while(function() { return 1; }, function() { [code] }); | |
* | |
* these async-friendly loop forms would be implemented by this library | |
* | |
* - yield statements convert values to functions in a similar way, so: | |
* | |
* yield(current); | |
* | |
* would become: | |
* yield(function() { return current; }); | |
* | |
* - the library would then generate code (using something like escodegen) to | |
* generate the modified code from the AST and construct a new Function object | |
* from the resulting code | |
* | |
* - this function would return a generator with the same interface as | |
* generators in ES6 | |
*/ |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment