52700.fb2 Учебник по Haskell - читать онлайн бесплатно полную версию книги . Страница 154

Учебник по Haskell - читать онлайн бесплатно полную версию книги . Страница 154

Вычисляется полностью означает все компоненты выражения участвуют в вычислении. Например то вы-

ражении, которое мы рассмотрели так подробно, вычисляется полностью. Приведём пример выражения, при

вычислении которого нужна лишь часть аргументов, для этого определим функцию:

isZero :: Nat -> Bool

isZero Zero

= True

isZero _

= False

Она проверяет является ли нулём данное число, теперь представим как будет вычисляться выражение, в

той и другой стратегии:

isZero (add Zero two)

Первая стратегия сначала вычислит все аргументы у add потом расшифрует add и только в самом конце

доберётся до isZero. На это уйдёт восемь шагов (семь на вычисление add Zero two). В то время как вто-

рая стратегия начнёт с isZero. Для вычисления isZero ей потребуется узнать какой конструктор в корне у

выражения add Zero two. Она узнает это за два шага. Итого три шага. Налицо экономия усилий.

Почему вторая стратегия экономит память? Поскольку мы всегда вычисляем аргументы функции, мы

можем не хранить описания в памяти а сразу при подстановке в функцию начинать редукцию. Эту ситуацию

можно понять на таком примере, посчитаем сумму чисел от одного до четырёх с помощью такой функции:

sum :: Int -> [Int] -> Int

sum []

res = res

sum (x:xs)

res = sum xs (res + x)

Посмотрим на то как вычисляет первая стратегия, с учётом того что мы вычисляем значения при подста-

новке:

sum [1,2,3,4] 0

=>

sum [2,3,4]

(0 + 1)

=>

sum [2,3,4]

1

=>

sum [3,4]

(1 + 2)

=>

sum [3,4]

3

=>

sum [4]

(3+3)

=>

sum [4]

6

=>

sum []

(6+4)

=>

sum []

10