Я играю с расширением ConstraintKinds GHC.
У меня есть следующий тип данных, который представляет собой всего лишь поле для вещей, выполняющих ограничение одного параметра c:
data Some (c :: * -> Constraint) where
Some :: forall a. c a => a -> Some c
Например, я мог бы построить поле с некоторым номером (возможно, не очень полезным).
x :: Some Num
x = Some (1 :: Int)
Теперь, пока c содержит ограничение Show, я мог бы предоставить экземпляр Show (Some c).
instance ??? => Show (Some c) where
show (Some x) = show x -- Show dictionary for type of x should be in scope here
Но как я могу выразить это требование в контексте экземпляра (помечено ???)?
Я не могу использовать ограничение равенства (c ~ Show), потому что они не обязательно равны. c может быть Num, что означает, но не равно, Show.
Edit
Я понял, что это вообще невозможно.
Если у вас есть два значения типа Some Eq, их невозможно сопоставить для равенства. Они могут быть разных типов, каждый из которых имеет собственное понятие равенства.
То, что применяется к Eq, применяется к любому типу класса, в котором параметр типа отображается в правой части первой стрелки функции (например, второй a в (==) :: a -> a -> Bool).
Учитывая, что нет способа создать ограничение, выражающее "эта переменная типа не используется за первой стрелкой", я не думаю, что можно написать экземпляр, который я хочу написать.