【发布时间】:2014-08-12 18:29:09
【问题描述】:
我正在尝试在类型族中定义一个函数,该函数在类型族中定义的 GADT 本身的幻像类型上具有多态性。
我的类型族定义大致如下:
class Channel t where
data Elem t a :: *
foo :: t -> Elem t a
bar :: Elem t a -> [a]
我有一个实例如下:
data MyChannelType = Ch
instance Channel MyChannelType where
data Elem MyChannelType a where
MyConstructor :: Char -> Elem MyChannelType Char
foo _ = MyConstructor 'a'
bar (MyConstructor c) = repeat c
编译器抱怨:
Couldn't match type ‘a’ with ‘Char’
‘a’ is a rigid type variable bound by
the type signature for foo :: MyChannelType -> Elem MyChannelType a
是否可以使用 Rank2Types 编写此函数或重新格式化我的数据类型以启用它?
编辑:响应 Ganesh 要求的澄清
我希望foo (bar Ch) :: [Int] 是非法的。
我一直在完全使用 Ganesh 建议的解决方案,但我受到以下更复杂示例的启发,该示例失败了;给定:
data MyOtherType = IntCh | StringCh
我有一个实例如下:
instance Channel MyOtherType where
data Elem MyOtherType a where
ElemInt :: Int -> Elem MyOtherType Int
ElemString :: String -> Elem MyOtherType String
foo IntCh = ElemInt 0
foo StringCh = ElemString "a"
bar (ElemInt i) = repeat i
bar (ElemString s) = repeat s
非常感谢,
迈克尔
【问题讨论】:
-
这在您当前的签名中无法实现。为了帮助理解重新制定它的选项,您希望
bar (foo Ch) :: [Int]产生什么? -
或者,你想让它非法吗?
标签: haskell typeclass type-families type-level-computation