JavaScript Using generator function
Consider the following custom Iterator.
function makeRangeIterator(start = 0, end = Infinity, step = 1) {
let nextIndex = start;
let iterationCount = 0;
const rangeIterator = {
next() {
let result;
if (nextIndex < end) {
result = { value: nextIndex, done: false };
nextIndex += step;
iterationCount++;
return result;
}
return { value: iterationCount, done: true };
}
};
return rangeIterator;
}
Here's how to use it.
const it = makeRangeIterator(1, 10, 2);
let result = it.next();
while (!result.done) {
console.log(result.value); // 1 3 5 7 9
result = it.next();
}
console.log("Iterated over sequence of size: ", result.value); // [5 numbers returned, that took interval in between: 0 to 10]
Now we can simplify this using a generator function instead.
Here's my solution (https://jsfiddle.net/ztm473uv/):
function* makeRange(start=0, end=Infinity, step=1) {
last=0
for (let i=start; i<end; i+=step) {
last++
yield i
}
return last
}
const gen=makeRange(1,10,3)
// usage
let stop=false
let result
while (! stop) {
result=gen.next()
console.log(result)
if (result.done) stop=true
}
Output
{
done: false,
value: 1
}
{
done: false,
value: 4
}
{
done: false,
value: 7
}
{
done: true,
value: 3
}
Notice that within the generator function, expressions are executed until it encounters yield, in which case resumes from there when next next() is called. Also, if a return value is returned, the iteration ends there. In our example, when the iteration ends, result.done is set to true.
Remember that the return value becomes the final value of the iterator. In our case it is: {done: true, value:3}. If no return value was specified then it would be {done: true, value: undefined}.