Совпадение шаблона Haskell с отрицательным числом
Компилятор Haskell генерирует ошибку для следующей функции:
balancedMax :: Int -> Int -> Int
balancedMax -1 _ = -1
balancedMax _ -1 = -1
balancedMax a b = max a b
Перевертывание знака решает проблему:
balancedMax :: Int -> Int -> Int
balancedMax 1 _ = -1
balancedMax _ 1 = -1
balancedMax a b = max a b
Почему сопоставление шаблонов происходит с отрицанием, и что такое обходное решение?
Ответы
Ответ 1
Он терпит неудачу, потому что он думает, что вы пытаетесь переопределить оператор минус, потому что f -1 = ...
анализируется как f - 1 = ...
.
Чтобы исправить это, вам просто нужно добавить круглые скобки:
balancedMax :: Int -> Int -> Int
balancedMax (-1) _ = -1
balancedMax _ (-1) = -1
balancedMax a b = max a b
То же самое происходит в выражениях. Чтобы вызвать balancedMax
с отрицательным литералом, вам понадобятся скобки.
Ответ 2
потому что f -1 = ...
анализируется как f - 1 = ....
Что, если вы не знаете, означает то же самое, что:
(-) f 1 = ....
который похож на определение такой функции:
somefunc x 1 = x + 1
Что бывает эквивалентно определению somefunc() следующим образом:
x `somefunc` 1 = x + 1
Это просто то, что с (-) вам не нужно писать обратные элементы при использовании в позиции infix, то есть между двумя его аргументами.
В двух первых книгах, посвященных книгам, которые я рассматривал, вы предупреждаете вас, что унарные - должны использоваться с круглыми скобками, например. (-3).