Skip to content

Instantly share code, notes, and snippets.

@dudelson
Created November 21, 2017 21:18
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save dudelson/78ff45b20c0ea168613e26e125e3a9ae to your computer and use it in GitHub Desktop.
Save dudelson/78ff45b20c0ea168613e26e125e3a9ae to your computer and use it in GitHub Desktop.
Illustration of functors in ocaml and comparison to functions
(* Basic demonstration of how to create and use functors,
* as well as how they parallel functions *)
(* Here are the two (equivalent) ways to define a function *)
let f x = x + 1
let g = fun x -> x + 1
(* The functor has the same two syntaxes as the function, except whereas a
* function takes one or more 'expressions' (each of which has a 'type') and
* outputs a 'value' ('values' are just the subset of 'expressions' which cannot
* be evaluated further, thus they also have 'types'), a functor take one or more
* 'module-expressions' (each of which has a 'module-type') and outputs a
* 'module-expression' (with a 'module-type'). 'module-expressions' are also
* called 'structures' and 'module-types' are also called 'signatures'.
*)
(* Unlike functions, ocaml cannot infer the types for parameters to a functor,
* so they always need to be explicitly declared. AFAIK at the time of writing,
* there are no "built-in" module types provided by the ocaml core language, so
* we will create our own simple module type *)
module type X = sig
val x : int
end
(* Here are the two (equivalent) ways to define a functor. Note how they're exactly
* the same syntactically as the function definitions above, except the signatures
* of the functor parameters always need to be made explicit. The signature of
* the return structure, however, does not need to be made explicit; note how it
* is present in the first definition and omitted in the second. *)
module IncX (M : X) : X = struct
let x = M.x + 1
end
module IncX2 = functor (M : X) -> struct
let x = M.x + 1
end
(* Here we use the functors we defined above to create some structures *)
module A = struct let x = 0 end
module B = IncX(A)
module C = IncX(B)
module D = IncX2(A)
module E = IncX2(D)
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment