One of the hardest parts of learning OCaml is figuring out what the infix operators do, since they're just a string of symbols and you can't find them with a Google search. This is my attempt to make a cheatsheet for whenever you're wondering what a random series of symbols means. Doing a search on this page should find basic info about any of the common OCaml operators.
Note that some libraries define their own operators, like how Jane Street's Command.Spec
defines ++
, +>
, and +<
. In cases like that, hopefully the library you're using will make it clear what the infix operators do.
General info about infix functions
In OCaml, a function is infix if its name starts with one of these characters:
= @ ^ ∣ & + - * / $ %
Followed by zero or more of these characters:
! $ % & * + - . / : ? @ ^ ∣ ~
When defining an infix function, you need to put ()
around the "name".
For example, in utop
:
# let (=<>@^|&~+-*/$%!?:.) a b =
a + b ;;
val ( =<>@^|&~+-*/$%!?:. ) : int -> int -> int = <fun>
# 1 =<>@^|&~+-*/$%!?:. 2 ;;
- : int = 3
Also, you can see the type of an infix operator in utop by again wrapping the function name in parentheses:
# (=<>@^|&~+-*/$%!?:.);;
val ( =<>@^|&~+-*/$%!?:. ) : int -> int -> int = <fun>
The official documentation for this is here, although this blog has a more accessible explanation.
Built-in infix operators
The built-in operators are defined in Pervasives
:
Refer to the documentation for the magic involved in functions that work on multiple types (=
, <>
, <
, >
, etc).
Operator | Description |
---|---|
= | Structural equality[1] |
<> | Structural inequality[1] |
< | Less than |
> | Greater than |
<= | Less than or equal |
>= | Greater than or equal |
== | Physical equality (same object)[1] |
!= | Physical inequality (not same object)[1] |
&& | Boolean and |
& | (Deprecated) Boolean and |
|| | Boolean or |
| | (Deprecated) Boolean or |
|> | Reverse function application (x |> f is the same as f x ) |
@@ | Function application (f @@ x is the same as f x ) |
~- | Integer negation (same as unary - ) |
~+ | Described as "unary addition" but doesn't seem to do anything. |
+ | Integer addition |
- | Integer subtraction |
* | Integer multiplication |
/ | Integer division |
~-. | Float negation (same as unary -. ) |
~+. | Described as "unary addition" but doesn't seem to do anything. |
+. | Float addition |
-. | Float subtraction |
*. | Float multiplication |
/. | Float division |
** | Float exponentiation |
^ | String concatenation |
@ | List concatenation |
! | Get the value of a ref |
:= | Set the value of a ref |
^^ | Format string concatenation |
Jane Street
Numbers
Jane Street generally defines arithmetic operators in modules where they make sense, so you can do things like:
Bigint.(of_int 1 + of_int 3 / of_int 5)
The documentation for this interface is under Int_intf.S_common
, although most of them are defined for floating point numbers too.
Operator | Description |
---|---|
+ | Module-specific addition (i.e. Float.(+) is float addition) |
- | Module-specific subtraction |
* | Module-specific multiplication |
/ | Module-specific division |
// | Integer division return float |
% | Infix mod (result is always positive) |
/% | Infix mod (result is negative if the input is negative) |
Monads
Jane Street's libraries (Core, Async, Base, etc.) consistently define infix operators under Monad_infix
modules.
Operator | Description |
---|---|
>>= | Infix version of bind . Opening Async sets this to Deferred.bind |
>>| | Infix version of map . Opening Async sets this to Deferred.map |
>>=? | bind mixed with Or_error . Opening Async sets this to Deferred.Or_error.bind |
>>|? | map mixed with Or_error . Opening Async sets this to Deferred.Or_error.map |
map
and bind
are documented assuming that you're familiar with monads, and you may find this StackOverflow answer useful if you need more information.
>>=
and >>|
show up most commonly in Async, but they can also be used with Option
, List
, Result
, etc.
Lwt
See the Lwt documentation.
Operator | Description |
---|---|
>>= | Infix version of bind |
=<< | bind with the arguments reversed |
>|= | Infix version of map . Same as >>| in Jane Street code |
=|< | map with the arguments reversed |
Lwt doesn't have Async's >>=?
or >>|?
because Lwt.t
can contain errors without having a separate Or_error
module.
See the Jane Street Monad section above if you need info about map
and bind
actually do.