如何使用函数类型依赖来导出类型参数的相等性?

Bry*_*ier 5 haskell

请考虑以下代码:

{-# LANGUAGE RankNTypes, MultiParamTypeClasses, FunctionalDependencies #-}

data St t = St
    {       use_t :: t
    }

class S s t | s -> t
    where   -- Nothing really

newtype P s = P
    {       unP :: forall b t. (S s t) =>
                    St t
            ->      (St t -> b)     -- pok
            ->      b
    }

f :: (S s t) => t -> P s
f t = P $ \s pok -> pok s { use_t = t }
Run Code Online (Sandbox Code Playgroud)

代码看起来很人为,但想法是该类S用于表示类型参数t由type参数确定s,因此我不必将t类型参数添加到类型中P.

但上面的代码总之给出了以下错误Could not deduce (t1 ~ t) from the context (S s t) or from (S s t1).此错误消息表明编译器想要使用这些上下文中的一个或另一个,而我希望它会使用两者并t1 ~ t从中得出结论.

我希望任何建议能够在不添加t类型参数的情况下使其工作P.

dfe*_*uer 3

你不能用所写的类来做到这一点。请参阅我可以通过函数依赖来神奇地实现类型相等吗?。但你可以用不同的类来做到这一点:

class t ~ T s => S s t where
  type T s :: *
Run Code Online (Sandbox Code Playgroud)

您需要T为每个实例进行定义,但这至少并不难。T如果有合适的定义,您可以提供默认定义。