Modules
From Textbook: OCaml Modules
Structures¶
Semantics¶
The first letter of a module’s name should be capitalized.
module ModuleName = struct
(* definitions *)
endYou can access the variables / methods in a module by Module.method
let x = ModuleName.empty;;
x.peek;;Signatures¶
Semantics¶
Signature is a collections of declarations; not evaluated, just type checked.
module type ModuleTypeName = sig
(* declarations *)
end
module type Stack = sig
type 'a stack
val empty : 'a stack
val is_empty : 'a stack -> bool
val push : 'a -> 'a stack -> 'a stack
val peek : 'a stack -> 'a
val pop : 'a stack -> 'a stack
endA structure matches a signature if the structure provides definitions for all the names specified in the signature (and possibly more), and these definitions meet the type requirements given in the signature.
If you don’t seal X, as long as the fields in module correspond with those in signature, these two match. when we seal X, we a create a linkage between module with the signature but we don’t have to do that. It’s safer if you explicitly want X to be a type of X, but we add an extra layer of abstraction to X.
Abstraction¶
You can also specify that this module as a type of some signature by providing a module type annotation : Stack. After adding this, everything inside that module will be come abstract and hidden from view.
module type Arith = sig
type t
val zero : t
val one : t
val (+) : t -> t -> t
val ( * ) : t -> t -> t
val (~-) : t -> t
end
module Ints : Arith = struct
type t = int
let zero = 0
let one = 1
let (+) = Stdlib.(+)
let ( * ) = Stdlib.( * )
let (~-) = Stdlib.(~-)
endOutside of the module Ints, the expression Ints.(one + one) is perfectly fine, but Ints.(1 + 1) is not, because t is abstract: outside the module no one is permitted to know that t = int. In fact, the toplevel can’t even give us good output about what the sum of one and one is!
# Ints.(one + one);;
- : Ints.t = <abstr>Sharing Constraint¶
OCaml lets you write sharing constraints that refine a signature by specifying equations that must hold on the abstract types in that signature. If T is a module type containing an abstract type t, then T with type t = int is a new module type that is the same as T, except that t is known to be int. For example, we could write:
module Ints : (Arith with type t = int) = struct
(* all of Ints as before *)
endNow both Ints.(one + one) and Ints.(1 + 1) are legal.
Modules and the Top Level¶
Well, apparently you cannot remember everything about how to import a library into OCaml and you don’t have to. So just refer to this site