Проблема с вашей подписью состоит в том, что список, переданный stripPrefixBy
, объявляется как список функций, которые принимают в качестве аргумента определенный a , а затем выдают Maybe b
для любого * 1005.* b звонящий выбирает.Единственные значения, которые могут возвращать функции в списке, это ⊥
, Nothing
и Just ⊥
.
То есть, когда используется неумеренный полиморфизм, forall
не означаетТо же самое он делает с экзистенциально квантифицированным типом: там forall
применяется к типу конструктора , то есть
data MyType = forall a. Foo a
Foo :: forall a. a -> MyType
, но здесь говорится, что функция должнав буквальном смысле слова типа forall b. a -> Maybe b
.
Вот исправленный пример использования экзистенциального типа:
{-# LANGUAGE ExistentialQuantification #-}
data Pred a = forall b. Pred (a -> Maybe b)
stripPrefixBy :: [Pred a] -> [a] -> Maybe [a]
stripPrefixBy [] xs = Just xs
stripPrefixBy _ [] = Nothing
stripPrefixBy (Pred p:ps) (x:xs) = case p x of
Just _ -> stripPrefixBy ps xs
Nothing -> Nothing
res :: Maybe String
res = stripPrefixBy [Pred $ const (Just 0), Pred Just] "abc"
wantThisToBeTrue :: Bool
wantThisToBeTrue = case res of
Just "c" -> True
_ -> False
Я считаю, что UHC поддерживает непосредственное выражение нужного типа,как
stripPrefixBy :: [exists b. a -> Maybe b] -> [a] -> Maybe [a]