views:

199

answers:

3

There is this index function in "Erlang Programming":

index(0, [X|_]) -> X;
index(N, [_|Xs]) when N>0 -> index(N-1, Xs)

Isn't the guard "when N>0" superfluous because of the pattern matching? Calling index(0, List) will never end up in the second clause so N will always be > 0. Or am I totally wrong here?

+6  A: 

The when clause guards against negative indices (edit: see comments to original question ;).

rak5hasa
+12  A: 

The function works correctly for N>=0. Without a guard, for N<0 it would traverse the whole list:

index(-2,[1,2,3]) -> index(-3,[2,3]) -> ... -> index(-5,[]) -> error.

That isn't a large problem, only you might get a confusing exception. In languages with infinite lists (Haskell, Ocaml), forgetting about that guard might lead to infinite loop: index(-1, [0,0,0..]).

sdcvvc
+5  A: 

It also gives clearer code as you explicitly say when this clause is valid, not just by default. Yes, I know that in some (many) cases this is not possible to do properly as the test may become very complex or that you want some form of default case. But not here.

rvirding