Reputation: 2280
Can everyone explain to me this piece of code ?
let safe_division n = function
| 0 -> failwith "divide by 0"
| m -> n / m
When I excute safeDiv 3 0
, what is the m
and n
in this case ?
In general case, when does the function match the first and second pattern ?
Upvotes: 9
Views: 8623
Reputation: 1746
let safe_division n = function
| 0 -> failwith "divide by 0"
| m -> n / m
is just equivalent to:
let safe_division n = fun x -> match x with
| 0 -> failwith "divide by 0"
| m -> n / m
Note fun
and function
are slightly different. See: Function definition.
Upvotes: 1
Reputation: 373
When you execute safe_division 3 0
, first, 3
is bound to the name n
and the right-hand side of the declaration is then evaluated.
This is a function
, so the next argument, 0
, is matched against the different cases, in order. Here, it matches the first case, so the right-hand side is evaluated and an exception is thrown. In this case, the name m
is never bound to anything.
If the second argument was, for example, 1
, then it would have matched the second case (this case matches every possible value anyway, it's a default case), binding the name m
to the value 1
and then returning the result of n / m
.
Upvotes: 11
Reputation: 36078
It is easy to see what this means once you realise that
let f x y z = e
is just a short-hand for
let f = function x -> function y -> function z -> e
That is, a function of n arguments actually is n nested functions of 1 argument. That representation is called "currying". It is what allows you to apply a function partially, e.g.
let g = f 3
returns a function of 2 arguments.
Of course, the short-hand above can be mixed freely with the explicit form on the right, and that's what your example does. You can desugar it into:
let safe_division = function n -> function
| 0 -> failwith "divide by 0"
| m -> n / m
Upvotes: 14
Reputation: 605
let safe_division n
define a function which type is int -> ...
function
| 0 -> failwith "divide by 0"
| m -> n / m
define a function which type is int -> int
So the resulting type of the whole is int -> int -> int where n is the first argument, and m the second. The last int is the result.
Upvotes: 7