Search code examples
haskellpattern-matchingwildcardstrictness

When is it useful to use "strict wildcard" in Haskell, and what does it do?


I was looking at some Haskell source code and came across a pattern match with !_, the code is here: http://hackage.haskell.org/package/base-4.9.0.0/docs/src/GHC.List.html#unsafeTake

take n xs | 0 < n     = unsafeTake n xs
          | otherwise = []

-- A version of take that takes the whole list if it's given an argument less
-- than 1.
{-# NOINLINE [1] unsafeTake #-}
unsafeTake :: Int -> [a] -> [a]
unsafeTake !_  []     = []
unsafeTake 1   (x: _) = [x]
unsafeTake m   (x:xs) = x : unsafeTake (m - 1) xs

I don't really understand how the "strict wildcard" works and why it's useful for this function (or any other function).


Solution

  • The idea is that unsafeTake (and take for that matter), when asked to return the first m elements of the empty list, it should return the empty list, no matter what the value of m is. But what if m is an expression that throws an exception? For example, it would be weird for unsafeTake undefined [] to return []. So we need to ensure that m evaluates to integer even if we don't care what is its exact value (for the empty list case of course). This makes unsafeTake behave the same way when it comes to its first argument, not matter whether the second argument (the list) is empty or not.