Is there a more elegant or better way to write a commutative function in F#/OCaml rather than listing all possible cases?
let commutative x y =
match x,y with
a, _ -> val1
|_, a -> val1
|b, _ -> val2
|_, b -> val2
...
|_,z -> |valN
While I was writing the question I thought one could make the function recursive and swap the arguments if no match is found.
let rec commutative x y =
match x,y with
a,_ -> val1
|b,_ -> val2
...
|nox,noy -> commutative noy nox
But if I adopt this approach I cannot have in the function a default case that matches with everything unless I add another argument whose value indicates if it's the second time the function is being called and return the default value instead of calling the function with the swapped args if that's the case.
Any other ideas? Does the language offer a construct for expressing the fact a function I'm defining is commutative?
(I'm answering for OCaml only as my F# is extremely rusty.)
There's no special help in OCaml for defining commutative functions.
If your parameter type has a reasonable ordering relation you can swap them if necessary to make x the larger (say). Almost all types can be compared in OCaml, so this should work very commonly. (Things that can't be compared: function types, cyclic values.)
I'm not sure this would help, but it might reduce the number of cases that you need to write out:
let commutative x y =
match (max x y, min x y) with
| A, _ -> value
. . .