ссылка на себя в функциях Haskell

Я изучаю Haskell и использую следующее выражение на Haskell Wiki действительно озадачил меня:

fibs = 0 : 1 : zipWith (+) fibs (tail fibs)

Я не могу понять, почему это работает.

Если я применяю стандартную логику каррирования (zipWith (+)) возвращает функцию, которая принимает список в качестве аргумента, а в Turn возвращает другую функцию, которая принимает в качестве аргумента другой список, и возвращает список ( zipWith: :( a -> b -> c) -> [a] -> [b] -> [c] ). Итак, fibs - это ссылка на список (который еще не был оценен), а (хвостовые аргументы) - это конец того же (неоцененного) списка. Когда мы пытаемся вычислить ( взять 10 fibs ), первые два элемента привязаны к 0 и 1 . Другими словами fibs == [0,1,?,? ...] и (хвостик) == [1,?,?,?] . После завершения первого сложения fibs становится [0,1,0 + 1,?, ..] . Точно так же после второго сложения мы получаем [0,1,0 + 1,1 + (0 + 1),?,? ..]

  • Верна ли моя логика?
  • Есть ли более простой способ объяснить это? (какие-либо идеи от людей, которые знают, что компилятор Haskell делает с этим кодом?) (ссылки и ссылки приветствуются)
  • Это правда, что этот тип кода работает только из-за ленивого вычисления?
  • Какие оценки случаются, когда я выдумал !! 4 ?
  • Предполагает ли этот код, что zipWith обрабатывает элементы с начала до конца? (Я думаю, что нет, но я не понимаю, почему)

РЕДАКТИРОВАТЬ2: Я только что нашел заданный выше вопрос и хорошо ответил здесь . Прошу прощения, если я потратил чье-то время.

РЕДАКТИРОВАТЬ: вот более сложный для понимания случай (источник: Форумы проекта Euler ):

filterAbort :: (a -> Bool) -> [a] -> [a]
filterAbort p (x:xs) = if p x then x : filterAbort p xs else []

main :: Int
main = primelist !! 10000
         where primelist = 2 : 3 : 5 : [ x | x <- [7..], odd x, all (\y -> x `mod` y /= 0) (filterAbort (<= (ceiling (sqrt (fromIntegral x)))) primelist) ]

Обратите внимание, что все (\ y -> x mod y / = 0) ... Как ссылка на x здесь НЕ может вызывать бесконечную рекурсию?

8
задан Community 23 May 2017 в 10:24
поделиться