JavaScript Iteration Protocol
Tags: javascript, programming, beginners, learning
Published: 2023-07-18 22:49:31

If there is a concept I have had to learn and relearn from time to time,  it is the concept of iteration in JavaScript. This time around I put in extra effort to ensure each idea and concept settles in my head. So, I made a chart 

![JavaScript Iteration protocols chart](https://dev-to-uploads.s3.amazonaws.com/uploads/articles/tphun1leasvg89nvu86w.png)

let me explain what each component in the chart is about. In case you need to learn more, I will leave a link at the end of this article.

For beginners' sake, protocols are sets of rules to follow to achieve something. So in this case, `Iteration protocols`.

## Iteration Protocols
In JavaScript, the `Iteration protocols` consist of `iterable protocol` and `iterator protocol`.
## Iterable protocol
This rule allows an object to customize how Javascript iterates over it. JavaScript will not iterate over any object that doesn't follow this protocol.

The rule states that,
> In order to be iterable, an object must implement a zero-argument method(function) named `@@iterator`, meaning that the object (or its parent) must have a property with a `@@iterator` key which is available via constant `Symbol.iterator` -- MDN web docs

This function must return an `iterator Object` which is important when looping with `for...of`.

## Iterable object
An object that obeys `iterable protocol`. Built-in types, such as `Array`, `String`, `Map`, and so on, are all `iterable objects` types. Below is an example of a custom object that is an `iterable Object`
```javascript
const iteratableObject = {
    *[Symbol.iterator](){
        yield 1
        yield 2
        yield 3
    }// we can also use normal function instead of generator function
}
```
INTERESTING FACT: `Generator function` obeys both iteration protocols
 
## Iterator protocol
This is the rule that must be followed to turn any object into an `iterator`.

The rule states that,

> In order to be an `iterator`, an object must implement a `next` method and optionally `return` and `throw` methods. These methods can take zero or one argument and must return an object that implements `IteratorResult` interface.

## Iterator Object
Any object that obeys `iterator Protocol` i.e implement at least the `next` method that returns `IteratorResult` object.
Example of Iterator object
```javascript
const iteratorObject = {
    next() {
        return {
            done: false,
            value: "hello"
        }
    }
}
```
## next, return and throw method
These are `iterator Object` methods. Of the three, only `next` is required for an `iterator Object`. 

- `next method`: get called to produce `IteratorResult` with the next value in the sequence.

- `return method`: when this method is defined, it gets called when `break` is used in `for...of` loop. It is used for clean-up operations like closing an open file descriptor, ending a connection to a database, and so on.

- `throw method` -  Gets called when there is an exception during iteration. This function is called to inform iterator object that an error has occurred. This is also for cleanup operations.

## IteratorResult Interface
`next`, `return`, and `throw` methods must return an object that implements this interface. The interface has two optional properties `value` and `done`. The presence or absence of one or both properties carries some meanings:
- when both properties  are missing, the default  will be 
```javascript
{ value: undefined, done: false }
```

### Done property
This property stores a boolean value. when it is `true`, it means we are done with the iteration and there are no values left to present. `false` means the opposite.

### Value property
This property can hold any valid JavaScript data type. This is the value we see when we loop over an `iterable Object` using `for...of` loop.
```javascript
const iteratableObject = {
    *[Symbol.iterator](){
        yield 1
        yield 2
        yield 3
    }
}

for ( const you of iteratableObject){
    console.log(you, "value from IteratorResult.value")
}
```

If you need more information on these components from the source, here is an [iteration protocols](https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Iteration_protocols) article on MDN web docs.

Let me know if you have any suggestions or questions in the comments.
You can reach me on [linkedin](https://www.linkedin.com/in/haastrupea/) and [Twitter: killcodeNG](https://twitter.com/killcodeNG).