Permalink
Find file Copy path
Fetching contributors…
Cannot retrieve contributors at this time
73 lines (47 sloc) 1.85 KB

Free

The Free monad is a monad that is able to separate instructions from their interpreter. There are many applications for this monad, and one of them is for implementing Trampolines, (which is a way to make recursion constant stack for languages that don't support tail call elimination, like JavaScript!).

Please see Ken Scambler's excellent talk and example project to get an in-depth understanding of this very useful monad.

Creating a Free monad

The Free monad has two constructors, Suspend and Return, which represents the continuation of a calculation and the completion of one, respectively.

Return(a: A): Free[F[_], A]
Suspend(f: F[Free[F,A]]): Free[F[_], A]
const a = Return(1)
const sum = Suspend(Identity(Return(1)))
// or
const sum = Free.liftF(Identity(1))

As you may see, Return wraps a value A, where as Suspend, wraps a Functor containing another Free.

Free.liftF

Free.liftF(f: F[A]): Free[F[_], A]

Lifts a Functor F into a Free.

Methods

map

Free[F[_], A].map(f: A => B): Free[F[_], B]

Performs a map across the value inside the functor.

flatMap

Aliases: bind, chain

Free[F[_], A].flatMap(f: A => Free[F[_], B]): Free[F[_], B]

Performs a monadic bind over the Free.

resume

Free[F[_], A].resume(): Either[F[Free[F[_], A]], A]

Evalutates a single layer in the computation, returning either a suspension or a result.

go

Free[F[_], A].go(f: F[Free[F[_], A]] => Free[F[_], A]) : A

Runs the computation to the end, returning the final result, using the supplied functor f to extract the next Free from the suspension.

...and undocumented

  • join
  • takeLeft
  • takeRight