I am wondering how the name of a type can be exposed from a module, without needing to reference it from the module level. For example, in the standard library there is a type for a list, within the module List, but when writing code using the standard library one can simply write functions with type annotations of 'a list. Without needing to use 'a List.list or 'a List.t or something like that.
list type is defined in the OCaml
core library (not to be confused with Jane Street’s Core library, despite the unfortunate name clash): OCaml - The core library
type 'a list =  | :: of 'a * 'a list
The members defined in the
core library are built-ins, i.e. they are always available in every OCaml program. There are a couple of ways to get a similar effect:
- Use the
open Modsyntax to open the module
Modin a large-enough scope so that its members are available from that point onwards in the file
- Use your build system’s ‘auto open’ functionality to have some modules automatically opened without having to explicitly
However, these practices are best avoided as much as possible, because opening lots of modules in scope leads to confusion about where items are coming from, and has a negative impact on readability of the code. It’s rather easier to tell where
Mod.t is coming from, than where
mod is coming from.
I generally agree with not opening lots of modules for readability. It can sometimes be helpful to expose a small number of things.
Thank you very much for your answer. It was very helpful.
Do you know of a way to not include core when compiling, similarly to how -nopervasives excludes the Stdlib?
I believe this is not possible at the moment.
It is not possible at all. You cannot remove core types without removing core features of the language. For instance, float literals relies on the existence of the float type or optional arguments depend on the option type.
On the other hand, you can hide a core type by reusing its name (although obviously this is an ugly thing to do ) : typing
type list = unit at the beginning of your code will force you to write
List.t rather than
list in your type annotations (which seems to be the asker’s original intent). Once your code is finished, you can remove the ugly prelude.
Sadly(?) this doesn’t force pretty-printing to use
List.t. Try that in
utop (OCaml 4.12):
# type list = | type list = | #  - : int list/2 =  # ( : _ List.t) - : int list/2 = List.(::) (0, )