Если у меня есть тип данных G
, реализованный с ограничением типа следующим образом:
data Ord v => G v = G [v] (M.Map v v)
И у меня есть функция отображения следующей подписи также с ограничением типа (реализация опущена)
mapG :: (Ord v, Ord v') => (v -> v') -> G v -> G v'
Затем я хочу реализовать G
как функтор, поэтому я делаю следующее
instance Functor G where
fmap = mapG
Это не скомпилируется, так как он жалуется
• No instance for (Ord a) arising from a use of ‘mapG’
Possible fix:
add (Ord a) to the context of
the type signature for:
fmap :: (a -> b) -> G a -> G b
Поэтому я попытался привязать ограничение типа к экземпляру следующим образом:
instance Ord v => Functor (G v) where
fmap = mapG
Но что еще хуже, компилятор жалуется:
• Expecting one fewer argument to ‘G v’
Expected kind ‘* -> *’, but ‘G v’ has kind ‘*’
• In the first argument of ‘Functor’, namely ‘G v’
In the instance declaration for ‘Functor (G v)’
Теперь у меня закончилась идея, как заставить это работать.Может кто-нибудь объяснить и предложить, как мне это изменить?
Замечания:
- Мне нужно реализовать это как еще большее количество экземпляров, а не только как Functor в качестве примера здесь, ввопрос.
- Требуется ограничение типа
Ord
(по причинам, не связанным с вопросом), поэтому я не могу его удалить.