Morgen Yang
Morgen Yang

Reputation: 333

What is the meaning of ~ before (l, r)

I read the library of Haskell

partitionEithers :: [Either a b] -> ([a],[b])
partitionEithers = foldr (either left right) ([],[])
 where
  left  a ~(l, r) = (a:l, r)
  right a ~(l, r) = (l, a:r)

What is the meaning of ~ before (l, r)?

Upvotes: 10

Views: 320

Answers (1)

luqui
luqui

Reputation: 60463

This is a lazy pattern match. It means that the pattern match is assumed to be successful, and only actually performed when its data is needed.

ghci> strictPat (a,b) = "hello"
ghci> lazyPat  ~(a,b) = "hello"

ghci> strictPat undefined
"*** Exception: Prelude.undefined
ghci> lazyPat undefined
"hello"

ghci> strictPat2 (a,b) = "the values are " ++ a ++ " and " ++ b
ghci> lazyPat2  ~(a,b) = "the values are " ++ a ++ " and " ++ b

ghci> strictPat2 undefined
"*** Exception: Prelude.undefined
ghci> lazyPat2 undefined
"the values are *** Exception: Prelude.undefined

It is used here so that partitionEithers can be a good streamer. Otherwise it would have to evaluate the whole list before it could return the first element of either of its results (because e.g. left would force the incoming pair, which was generated by a recursive call, which would have to force its incoming pair, and so on...).

Upvotes: 18

Related Questions