Изучение Haskell: круговая программа - помогите объяснить

В настоящее время я изучаю книгу Дуца и Ван Эйка «Дорога к логике, математике и программированию на Хаскеле». До этой книги я никогда не сталкивался с каким-либо функциональным языком программирования, так что имейте это в виду.

Еще в начале книги, он дает следующий код для проверки простоты:

ldp :: Integer -> Integer
ldp n = ldpf primes1 n

ldpf :: [Integer] -> Integer -> Integer
ldpf (p:ps) n | rem n p == 0 = p 
              | p^2 > n      = n
              | otherwise    = ldpf ps n

primes1 :: [Integer]
primes1 = 2 : filter prime [3..]

prime :: Integer -> Bool
prime n | n < 1     = error "not a positive integer"
        | n == 1    = False 
        | otherwise = ldp n == n

Кажется, что циклическое программирование происходит в том, что ldp вызывает primes1, который вызывает prime, и снова вызывает ldp. Хотя книга предлагает это как объяснение того, почему программа выполняется и завершается:

ldp делает вызов primes1, списка простых чисел. Это первая иллюстрация «ленивого списка». Список называется «ленивым», потому что мы вычисляем только ту часть списка, которая нам нужна для дальнейшей обработки. Чтобы определить простые числа1, нам нужен тест на простоту, но этот тест сам по себе определяется в терминах функции LD, которая, в свою очередь, относится к простым числам1. Кажется, мы бегаем по кругу. Этот круг можно сделать не порочным, избегая критерия примитивности для 2. Если задано, что 2 простое, то мы можем использовать примитивность 2 в проверке LD, что 3 простое, и так далее, и мы находимся и работает

Хотя я думаю, что понимаю это объяснение, я был бы очень признателен, если бы кто-то мог объяснить с точки зрения мирян:

Что такое «ленивый список» и как он применяется в этом контексте?Как знание, что 2 простое, позволяет программе быть не порочной?

Любые ответы с благодарностью.

Ответы на вопрос(3)

Ваш ответ на вопрос