разница между isNothing и (==ничего) в Haskell?
Я смущен тем, почему две функции ниже включают Nothing иначе:
coalesce m1 m2 = if isNothing m1 then m2 else m1
coalesce' m1 m2 = if (m1 == Nothing) then m2 else m1
первый имеет вид:
λ> :t coalesce
coalesce :: Maybe a -> Maybe a -> Maybe a
как и ожидалось. Но у второго есть:
λ> :t coalesce'
coalesce' :: Eq a => Maybe a -> Maybe a -> Maybe a
почему через (==Nothing) вводим Eq a ограничения?
(GHC 8.2.2)
3 ответов
== функция Eq a => a -> a -> Bool. Вы делаете один из его операндов Nothing, Так что a это Maybe b для некоторого типа b, но это Eq a ограничение по-прежнему действует – в Maybe b есть Eq экземпляра. Maybe b содержит определение для такого экземпляра – Eq (Maybe b) для всех Eq b.
другими словами, == - это просто функция, и она не знает заранее, что вы предоставляете Nothing в качестве аргумента. Это знает только он некоторые Maybe a, и он должен иметь возможность сравнивать равенство, если это случается Just ….
другими словами, Вот как вы можете определить == это уже существует для Maybes:
equals a b = case a of
Nothing -> isNothing b
Just x -> case b of
Nothing -> False
Just y -> x == y
обратите внимание, как x == y кажется, смысл должен быть Eq экземпляр для типа x и y.
потому что типа == и
(==) :: (Eq a) => a -> a -> Bool
ваше второе определение (coalesce') использует ==, поэтому он наследует Eq ограничение на его аргументы из ==.
строго говоря coalesce' использует == по значениям типа Maybe a, но есть экземпляр
instance (Eq a) => Eq (Maybe a) where ...
так Eq (Maybe a) ограничения Eq a, потому что это то, что необходимо для поддержки == on Maybe a.