Subtle points and items difficult to find via web search (in progress)
Also see Pierre Weis’s Frequently asked Questions about Caml.
Polymorphic compare: TODO (bluddy will fill in.)
let: When a
letexpression begins in the final branch of an
ifexpression, a semicolon will not terminate the
let; instead the
letexpression will include the code that comes after the semicolon. One might expect that the semicolon ends the
ifexpression, and that the code following it will execute after the entire
ifexpression, but instead that code is part of the
ifexpression. This can introduce subtle bugs, although it is a consequence of the normal (and useful) scoping rule for
let. To make the semicolon follow the entire
ifwith the embedded
let, wrap the
letexpression in parentheses or
end. For more, see if with semicolons.
Weak type variables: What is “the value restriction”? Why do some of my type variables start with underscore? What is the difference between a function with (for example) type
'a -> 'b, and one with type
'_weak1 -> '_weak2? Why am I getting a compiler error like these? (It worked when I tried it out in utop!)
Values do not match: val foo : '_weak1 -> '_weak1 is not included in val foo : 'a -> 'a
This means that your function (or any other value that gets this type) is not really polymorphic, and the compiler doesn’t have enough information to infer its concrete type, thus it represents the unknown parts of the type with so called “weak type variables”, the placeholders the need to be filled in by you. (The compiler will do it itself, if possible, but when you see the weak type in the error produced by the compiler, it means that it wasn’t possible, and your help is needed).
The Weak Type Variables article describes in detail why they exist in OCaml and how to cope with them.
Bits of syntax
Printf directives: Where can I find a list of
sprintf, etc. directives such as
See the Printf module documentation in the OCaml Manual.
Infix operators: Where can I find documentation on standard infix operators such as
For general documentation on operators, see the OCaml manual: Operators in the Expressions section, Index of values, or the Pervasives module documentation. For the Pervasives document, you’ll want to search the page for “operator” or for the specific operator you’re interested in.
For operator precedence and associativity, see the Expressions section of the manual, and scroll down past the BNF syntax specification or search for “Construction or operator”. The Pervasives module also specifies precedence and associativity in the documentation for each operator.
(Also possibly useful: Built-in operators and functions at OCaml for the Skeptical.)
ppx: What are these
[@@ ...]expressions that I see in people’s code? What does it mean when there’s a percent sign in the middle of a name, as in
let%lwt? What are extension points?
+’a, -‘a: Why are some type variables prefaced by “+” or “-“, as in
type +'a t?
These are called “variance annotations”. They’re used to constrain subtyping relations. See +’a and -‘a at the Jane Street Tech Blog.
open!: What’s the difference between
Both make the values and types in
My_moduleavailable without having to write “My_module.” in front of them.
open My_modulewill trigger a warning if
My_moduleoverrides existing definitions.
open!suppresses this warning. See Overriding in open statements from Chapter 8 Language extensions in the OCaml manual.
open!also suppresses another warning as well. This is a warning that no definition in the opened module is in fact used within
open!’s scope. There is some disagreement about whether this behavior is desirable. Those who use
open!for this purpose use it to open modules such as
Containersthat shadow many built-in definitions, using such a module as a way of providing an alternative standard programming environment. See the discussion at this OCaml PR: Fix PR6638: “unused open” warning was incorrectly suppressed by “open!”.