Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

patterns vs. guards: otherwise does not match?

The following two functions behave differently when given an empty string:

guardMatch l@(x:xs) 
    | x == '-'        = "negative " ++ xs
    | otherwise       = l

patternMatch ('-':xs) = "negative " ++ xs
patternMatch l        = l

Here my output:

*Main> guardMatch ""
"*** Exception: matching.hs:(1,1)-(3,20): Non-exhaustive patterns in function guardMatch

*Main> patternMatch ""
""

Question: why does not the 'otherwise' close catch the empty string?

like image 944
Vladimir Bychkovsky Avatar asked Nov 29 '22 03:11

Vladimir Bychkovsky


1 Answers

The otherwise is within the scope of the pattern l@(x:xs), which can only match a non-empty string. It might help to see what this (effectively) translates to internally:

guardMatch   l = case l of
                   (x  :xs) -> if x == '-' then "negative " ++ xs else l
patternMatch l = case l of
                   ('-':xs) ->                  "negative " ++ xs
                   _        ->                                         l

(Actually, I think the if is translated to a case + guard instead of the other way around.)

like image 132
geekosaur Avatar answered Dec 06 '22 07:12

geekosaur