Мы привыкли, что правая свертка (foldr) хорошо заточена для работы с бесконечными списками:
> let mapPlusPi = foldr (\x xs -> (x+pi):xs) []
> head $ mapPlusPi [1..]
4.141592653589793
К сожалению, иногда возникают неприятности. Вот функция, которая берет список и выкидывает из него элементы стоящие на нечетных местах:
> let evenOnly = snd . foldr
(
Read more... )
Comments 14
Reply
Reply
let evenOnly = snd . foldr (\x z -> let (os,es) = z in (x:es,os)) ([],[])
В оригинальном примере явный pattern matching в параметре автоматически делает функцию строгой по второму аргументу. Что происходит внутри -- хорошо видно при вызове ghc -O -ddump-stranal. В первом случае demand на параметер -- (S,1*U), во втором -- (L,U(1*U,1*U)).
Reply
а почему именно - надо подумать.
Reply
Т.е. например вот здесь:
let bla = foldr(\x (y:t) -> x:t) [0]
понятно, что поскольку у списка есть два конструктора, то нужно убедиться, что y:t, а не []. А вот у тупля только один конструктор, так что, не ясно, что его останавливает лениво матчить.
Reply
Reply
Reply
Reply
большая непривычность (но не сложность!) рассуждения за costs semantics.
Что довольно сильно, не буду спорить.
Reply
" = "
Reply
Reply
Leave a comment