I have been having difficulty understanding why the haskell expression let (x,y) = (y,1) in (x,y)
converges to (1,1)
as expected but fix (\(x,y)-> (y,1))
results in <<loop>>
being thrown. Can anyone explain this?
By default, the outermost patterns used in let
bindings are lazy. However, patterns used in lambda bindings are strict, so the pattern match against the tuple forces too much too early. You can explicitly write a lazy pattern match by prefixing it with ~
, making the lambda pattern equivalent to the let
pattern:
ghci> fix (\(~(x, y)) -> (y, 1))
(1,1)
This defers the actual evaluation of the pattern match until one of bound variables is forced, instead of when the function is called, avoiding the loop.
For more information, see the Haskell wiki article on lazy patterns.
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With