# OCaml Tutorial: Function

This page gives a practical understanding of functions in Ocaml.

## Function with One Parameter

To define a function, use the form:

`function `

`parameter_name` = `expression`

(* a function that returns its argument + 1 *) function n -> n + 1 ;; (* applying the function to the value 2 *) (function n -> n + 1) 2;; (* ⇒ 3 *)

## Function with More Than One Parameters

To define a function with 2 parameters, you do it by defining a function with 1 parameter, that returns another function of 1 parameter. The form is this:

`function `

`parameter` -> function `parameter` -> `expression`

The following is a example:

(* defining a function “f(x,y)” that computes x + y *) function x -> ( function y -> x + y );; (* applying the function to values *) (function x -> ( function y -> x + y) ) 3 4;; (* ⇒ 7 *)

In the above example, the line `function x -> ( function y -> x + y )`

, means a function with parameter x, which returns `function y -> x + y`

, which is a function with parameter y, and computes `x + y`

.

The number of parameters of a function is called its “arity”. So, a function with 2 parameters is a function of arity 2.

To define a function with 3 or more parameters, the same pattern is used.

`function `

`parameter_1` ->
function `parameter_2` ->
function `parameter_3` ->
…
-> `expression`

At the language core, all multi-parameter functions are decomposed into a sequence of functions of 1 parameter.

There is a syntax shortcut for defining functions of multiple parameters. The form is:

`fun `

`parameter_1` `parameter_2` `parameter_3` … -> `expression`

Example:

fun x y -> x + y;; (fun x y -> x + y) 3 4;; (* ⇒ 7 *)

This is the more practical way to define a function.

## Assign Name to Function

A function can be assigned to a variable, thus giving it a name.

let sumOfTwo = fun x y -> x + y;; (* giving function a name *) sumOfTwo 3 4;; (* ⇒ 7 *)

## Syntax Shortcut for Defining a Function

The form `let `

is used often, so that there is a shortcut. The shortcut form is:`name` = fun `params` -> `expr`

`let `

`function_name` `param1` `param2` … = `expression`

Example:

(* the following are equivalent *) let sumOfTwo = function x -> function y -> x + y;; let sumOfTwo = fun x y -> x + y;; let sumOfTwo x y = x + y;; sumOfTwo 3 4;; (* ⇒ 7 *)

## Operator Precedence of Function Syntax

The operator for function definition `->`

is more sticky to the right. This means, when you have

, ocaml will interpret it as `expr1` -> `expr2` -> `expr3`

.
This means when you define a function that returns a function, you don't have to use parenthesis.`expr1` -> ( `expr2` -> `expr3` )

However, function application in ocaml favors the left side.
If you write `f g h x;;`

, ocaml will interpret it as
`((f g) h) x;;`

. This is particular important to know when
you use functions of multiple arguments. Here's some examples:

let f s = s ^ "1";; (* append 1 to a string *) let g s = s ^ "2";; (* append 2 to a string *) let h s = s ^ "3";; (* append 3 to a string *) h (g (f "x"));; (* ⇒ "x123" *)

In the above, if you use `f g h "x";;`

, the compiler will give a error:

```
# Characters 0-1:
f g h "x";;
^
Error: This function is applied to too many arguments,
maybe you forgot a `;'
```

Because it starts by computing `f(g)`

. This results in a error right away, because
by your definition, f has one parameter of type string, and returns a string, but you are trying to apply the result to `h "x"`

.

If you call `((f g) h) "x"`

, then the error is more clear:

```
((f g) h) "x";;
^
Error: This expression has type string -> string but is here used with type
string
```

The error says “but is here used with type string” because your function g is defined to be of type “string → string”, and you are feeding g to f, which expect a string.

## Using Operator as Function

Operators, such as “+ *” etc, can be considered as functions of 2 parameters. They can be used as a function in ocaml. A function call has the form “f arg1 arg2”, while operator such as “+” is used in the form “arg1 + arg2”. Sometimes it is useful to call operators in the function form, so that the power of function and its syntax fully apply to all operators.

To use operator in the form of a function, the operator must be bracketed with paren. The form is:

`(`

`operator_symbol`) `arg1` `arg2`

Example:

( + ) 3 4;; (* ⇒ 7 *) ( *. ) 23. 3.;; (* ⇒ 69. *) ( + ) ((+) 3 4) 5;; (* ⇒ 12 *) ( * ) ((+) 3 4) 5;; (* ⇒ 35 *)

Note that extra paren for grouping is necessary.

## Defining Your Own Operator

You can define your own operator. The form is:

`let ( `

`symbol_chars` ) `left_arg` `right_arg` = `expression`

Example:

(* define operator for vector addition of 2 dimensional vectors *) (* using 2-tuple as vectors *) let ( @+ ) vec1 vec2 = ( (fst vec1)+(fst vec2), (snd vec1)+(snd vec2) ) ;; (3,4) @+ (5,6);; (* ⇒ (8,10) *)

Note: the char sequence used for operator is limited to symbol chars, such as “! @ # $ % ^ & *”. They cannot be letters, numbers, nor Unicode char.

## Recursive Function

Functions that are defined by referring to itself, must be declared with “rec”.

(* example of factorial function *) let rec f n = if n == 1 then 1 else n * f (n-1);; f 3 (* ⇒ 6 *) (* example of fibonacci sequence. *) (* nth term is sum of previous 2 terms. Starting with 0 and 1. *) let rec f n = match n with 0 -> 0 | 1 -> 1 | x -> f (n-1) + f (n-2);; f 9;; (* ⇒ 34 *)

Note: above recursive definitions are for example only. They are very inefficient.