In Real World Haskell, they describe combinators like this:
In Haskell, we refer to functions that take other functions as arguments and return new functions as combinators.
And then later they state that maybeIO
function is a combinator and its type signature looks like this:
maybeIO :: IO a -> IO (Maybe a)
But all I can see is that maybeIO
is a function that takes a value wrapped in IO monad and returns a value in IO monad. Then how does this function become a combinator ?
A combinator is a higher-order function that uses only function application and earlier defined combinators to define a result from its arguments.
The functional pattern representing a style of organizing libraries centered around the idea of combining functions.
Parser combinators allow us to compose many simple functions together to define our entire grammar. The underlying algorithm is Recursive Descent with backtracking, using techniques that are available to us in languages with first class functions like javascript.
It's represented as a function that takes some input and either returns a list of errors, if Left , or the result of parsing the input together with the rest of the input (that was not parsed), if Right .
There are really 2 things that we could mean when we say combinator. The word is a bit overloaded.
We usually mean a function which "combines" things. For example your function takes in an IO
value and builds up a more complex value. Using these "combinators" we can combine and create new complex IO
values from relatively few primitive functions to create IO
values.
For example, rather than creating a function which reads 10 files, we use mapM_ readFile
. Here combinators are functions that we use to combine and build values
The stricter computer sciencey term is a "function with no free variables". So
-- The primitive combinators from a famous calculus, SKI calculus.
id a = a -- Not technically primitive, genApp const const
const a b = a
genApp x y z = x z (y z)
This is part of a grander field called "Combinatory logic" in which you seek to essentially eliminate free variables and replace it with combinators and a few primitive functions.
TLDR: usually when we say combinator, we refer to a more general notion called the "combinator pattern" where we have a handful of primitive functions and a lot of user-defined functions to build up more complex values.
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With