Functors Exercise 1
// Exercise 1
// ==========
// Use _.add(x,y) and map(f,x) to make a function that increments a value inside a functor
console.log("--------Start exercise 1--------")
var ex1 = undefined
assertDeepEqual(Identity(3), ex1(Identity(2)))
console.log("exercise 1...ok!")
We want to add 1
inside Identity
.
var ex1 = map(_.add(1), Identity(3))
We need to map
so that we can add 1 to the value inside Identity(3)
_.add
is just the add function from lodash or ramda...
But we want to be able to increment any functor that comes in.
var ex1 = map(_.add(1))
This is the solution. map
is curried because it takes more than one argument (and we're only giving it one). So, later we can call ex1(Identity(2))
and it will be able to work with value inside Identity(2)
. Furthermore, _.add(1)
is also a curried function, waiting to be run when it recieves the second argument (Identity(2)
).
Remember two notes before, where we defined map
with curry. Not the .map
method, but the map()
function!
// from before...
var map = _.curry(function (f, obj) {
return obj.map(f)
})
Identity
is just a neutral functor, to be used for the exercises. It has no added behaviour, just to let you get used to using containers.
map(function (x) {return x.toUpperCase()}, Identity("firehose"))
// Identity(FIREHOSE)
So x
became "firehose" in the map
.
map(function (x) {return x.reverse()}, Identity([6,5,4,3]))
// Identity([3,4,5,6])
Emphasises that map
is not the map
that iterates over lists. It runs a function over an element of a data structure. As a reply to a question, we don't need to deal with this
with functional programming.
Why and when to use
Identity
?
It lets you lift values into the functional world. It's a neutral functor, when you need a functor and don't want any side effects.