# Golang - Iterator Pattern

In the world of software engineering, design patterns are quite common. One of the most popular patterns is the "Iterator Pattern" which is part of the "Gang of Four" patterns. This pattern is used to traverse a collection of objects without exposing its internal structure. In this article, we will discuss how to implement the Iterator Pattern in Golang.

# Understanding the Iterator Pattern

The Iterator Pattern provides a way to access the elements of an aggregate object sequentially without exposing its underlying implementation. The basic idea is to provide an interface for accessing the elements of a collection, and this interface is called the Iterator. The Iterator interface defines methods that allow us to traverse a collection, such as `Next()`, `HasNext()`, and `Current()`. The actual implementation of the traversal is encapsulated within the Iterator, and the client code just uses the Iterator to access the elements of the collection.

# Implementing the Iterator Pattern in Golang

In Golang, we can implement the Iterator Pattern using an interface, which defines the methods that are required for traversing the collection. Here is an example of the Iterator interface:

```go
type Iterator interface {
    Next() interface{}
    HasNext() bool
}
```

The `Next()` method returns the next element in the collection, and the `HasNext()` method checks whether there are more elements to traverse.

We can then implement the Iterator interface for a specific collection type. In this example, we will use a generic slice:

```go
type Slice[T any] []T

func (s Slice[T]) Iterator() Iterator[T] {
    return &sliceIterator{T, slice: s, index: -1}
}

type sliceIterator[T any] struct {
    slice Slice[T]
    index int
}

func (i *sliceIterator[T]) Next() T {
    i.index++
    return i.slice[i.index]
}

func (i *sliceIterator[T]) HasNext() bool {
    return i.index+1 < len(i.slice)
}
```

The `Slice[T]` type is a generic slice, and it has a method `Iterator()` which returns an instance of an iterator for this slice. The `sliceIterator[T]` type implements the Iterator interface for the `Slice[T]` type. The `Next()` method returns the next element of type `T` in the slice, and the `HasNext()` method checks whether there are more elements to traverse.

# Using the Iterator Pattern in Golang

Now that we have implemented the Iterator Pattern, we can use it to traverse the collection. Here is an example of how to use the `Slice[T]` type and its iterator:

```go
func main() {
    s := Slice[int]{1, 2, 3, 4, 5}
    it := s.Iterator()

    for it.HasNext() {
        fmt.Println(it.Next())
    }
}
```

In this example, we create an instance of the `Slice[T]` type and its iterator. We then use a loop to iterate over the collection and print each element.

# Conclusion

In conclusion, the Iterator Pattern is a useful pattern for traversing a collection without exposing its internal structure. In Golang, we can implement this pattern using an interface and a specific implementation for the collection type. By using the Iterator Pattern, we can write more modular and cleaner code, which is easier to maintain and extend.

---

# References

* [**“Design Patterns: Elements of Reusable Object-Oriented Software**](https://amzn.to/3SJenIZ)” by Erich Gamma, John Vlissides, Ralph Johnson, and Richard Helm
