Я пытаюсь разработать простую среднюю функцию в Haskell. Это, кажется, работает:
lst = [1, 3]
x = fromIntegral (sum lst)
y = fromIntegral(length lst)
z = x / y
Но почему следующая версия не работает?
lst = [1, 3]
x = fromIntegral.sum lst
y = fromIntegral.length lst
z = x / y
Вас сбивают с толку правила приоритета haskell для операторов.
Когда вы пишете
x = fromIntegral.sum lst
, Haskell видит то же самое, что и:
x = fromIntegral.(sum lst)
То, что вы хотели написать, было:
x = (fromIntegral.sum) lst
.
(композиция) имеет меньший приоритет, чем применение функции, поэтому
fromIntegral.sum lst
интерпретируется как
fromIntegral . (sum lst)
что неверно, поскольку sum lst
не является функцией.
Я просто хотел добавить "$ на помощь! ":
x = fromIntegral $ sum lst
y = fromIntegral $ length lst
Он имеет наименьший приоритет и существует, чтобы избежать слишком большого количества уровней скобок. Обратите внимание, что в отличие от (.), он не делает композицию функции, он вычисляет аргумент справа и передает его функции слева. Тип говорит обо всем:
($) :: (a -> b) -> a -> b
(.) :: (b -> c) -> (a -> b) -> a -> c