Idiomatic: pattern matching with two function heads or boolean guard clause?

I just found myself writing this:

def foo([], _), do: []
def foo(_, 0), do: []

But then I thought I could also use a guard clause with a boolean OR, like so:

def foo(list, n) when list == [] or n == 0, do: []

Is either version more idiomatic?
Would it maybe depend on the amount of code in the function? (DRY and all)

Because pattern matching is so nice and in this case the function body is very small I’ll probably choose the first version.

Thanks!

I use both of these idioms – and others – quite often. My main heuristic is: “is the code readable?”

The only non-idiomatic Elixir in such cases would be a load of if-s. The rest is quite fine and the exact idiom should vary depending on your priorities and the situation.

3 Likes

Second one is easier to understand I would say. More idiomatic… I don’t know, either one is fine.

The first one, as it leaves more room for optimisation by the compiler. Also matching 0 in the function head is more strict than x == 0 since 0.0 == 0.

PS: sometimes, if from business perspective both cases are to treat the same and not only by accident, I tend to use a guard using ===, as it better communicates indent of treating this cases the same.

4 Likes

Thanks all!

Yeah readability is definitely important.

Other things being equal (like readability) leaning towards faster code is good of course.

@NobbZ good catch of the x == 0!