# What the Functor?

A week ago I wrote an article on implementing Maybes in JavaScript, and while it was generally well received, it did draw some (well justified) criticism from some commenters. Specifically, there are some well-defined mathematical rules that my Maybe didn't obey. Terminology and nomenclature are always important if we want to communicate effectively with others, so although my Maybe has some utility, I wanted to learn some more about these mathematical rules so that:

- Code I write is interoperable with existing functional libraries
- I can understand the writing of others
- My writing is understandable to others
- It's interesting and fun!

One of the recommendations I received was to look at the Fantasy Land Specification which defines a set of algebraic data types. This a very technical specification and I'm not afraid to say parts of it go over my head at the moment, so I started with the most basic types. One of the simplest, and yet seemingly most commonly used and well known, is the Functor.

If a type is to become a functor, it need only do one thing: it must have a `map`

method. This method has one argument (arity-1), which must be a function, and must return another functor of the same type. I use TypeScript a lot, and so we can define an interface for a functor in that language:

```
interface Functor<T> {
map: <U>(fn: (a: T) => U) => Functor<U>;
}
```

We can now make concrete implementations of data structures that implement this interface, and be confident that if type-checking passes then we are obeying the rules. We'll start with a simple type that will wrap a number, and give us a simple way to inspect the value:

```
class NumberFunctor implements Functor<number> {
private value: number;
constructor(value: number) {
this.value = value;
}
inspect() {
console.log(this.value);
return this;
}
}
```

We now need to implement a map method - this method will take a function, pass it the internal value we are holding, and return a new instance of NumberFunctor:

```
class NumberFunctor implements Functor<number> {
private value: number;
constructor(value: number) {
this.value = value;
}
inspect() {
console.log(this.value);
return this;
}
map(fn) {
return new NumberFunctor(fn(this.value));
}
}
```

It can be used like this:

```
const twenty = new NumberFunctor(20);
twenty.map(x => x + 1).inspect(); // 21
twenty.map(x => x * 2).inspect(); // 40
```

Because we are returning a new functor each time, we can also chain map calls together:

```
const fifty = new NumberFunctor(50);
fifty
.map(x => x * 2)
.inspect() // 100
.map(Math.sqrt)
.inspect(); // 10
```

The key point is that when a type implements Functor, it means that it has a way of transforming the value(s) that it contains. When we use the `map`

method we don't have to care about how this transformation occurs - that is the internal responsibility of the specific functor.

To illustrate this further let's make a very simple Tuple functor that will hold two values - a first and a second:

```
class Tuple implements Functor<number> {
private first: number;
private second: number;
constructor(first: number, constructor: number) {
this.first = first;
this.second = second;
}
inspect() {
console.log(`Tuple: (${this.first}, ${this.second})`);
return this;
}
}
```

How are we going to implement `map`

for our tuples? We're going to apply the provided function to each of the values we hold, and return a new tuple with the results:

```
class Tuple implements Functor<number> {
private first: number;
private second: number;
constructor(first: number, constructor: number) {
this.first = first;
this.second = second;
}
inspect() {
console.log(`Tuple: (${this.first}, ${this.second})`);
}
map(fn) {
return new Tuple(
fn(this.first),
fn(this.second)
);
}
}
```

We can use it just like the NumberFunctor:

```
const tuple = new Tuple(49, 100);
tuple.map(x => x * 2).inspect(); // Tuple (98, 200)
tuple.map(Math.sqrt).inspect(); // Tuple (7, 10);
```

Hopefully at this point you are thinking about where we have seen a `map`

method before, and perhaps you realised you have used `Array#map`

:

```
[1,2,3].map(x => x * 2); // [2,4,6]
```

It's easy to see now that JavaScript arrays implement the Functor interface, and they implement a `map`

method that applies the function to each of the values they hold, and return a new array.

Thanks to everyone who read and commented on the original Maybe article, especially to those who wrote insightful and constructive comments.

### Subscribe to Developing Thoughts

Get the latest posts delivered right to your inbox