普遍存在的约束

时间:2013-05-09 09:43:39

标签: haskell polymorphism typeclass

这是一个非常有用的课程:

class Foo f a where
  foo :: f a

让我为很多类型制作默认值。事实上,我甚至可能不需要知道a是什么。

instance Foo Maybe a where
  foo = Nothing

现在我对所有Maybe a都有一个a,我可以稍后对它进行专门化。

specialize :: (forall a. f a) -> f Int
specialize x = x

fooMaybe :: Maybe Int
fooMaybe = specialize foo

嗯...... fooMaybe肯定看起来非常具体。让我们看看我是否可以使用上下文来概括它:

fooAll :: (Foo f a) => f Int
fooAll = specialize foo

糟糕!猜不是。

Foo.hs:18:21:
    Could not deduce (Foo * f a1) arising from a use of `foo'
    from the context (Foo * f a)
      bound by the type signature for fooAll :: Foo * f a => f Int
      at Foo.hs:17:11-28

所以,我的问题是,如何编写fooAllfooMaybe的广义版本?或者,更一般地说,如何普遍推广类型类约束

1 个答案:

答案 0 :(得分:7)

目前Haskell没有好办法。 constraints包提供的类型可能为do what you need,但我最近想出了如何打破它。仍然可能是你最好的选择,因为如果有人知道如何做到这一点它可能会得到更新

fooAll :: Forall (Foo f) => f Int
fooAll = specialize foo_f where
  foo_f :: forall a. f a
  foo_f = foo \\ (inst `trans` (Sub Dict) :: () :- Foo f a)