我正在尝试使用TypeApplications
来消除我正在调用的类型类实例之间的歧义。不幸的是,似乎实例声明的类型参数不能在实例主体中使用。具体来说,在这个玩具示例中:
{-# LANGUAGE FlexibleInstances #-}
{-# LANGUAGE TypeApplications #-}
{-# LANGUAGE UndecidableInstances #-}
class Foo a where
foo :: String
instance Foo () where
foo = "()"
instance Foo Int where
foo = "Int"
class Bar b where
bar :: String
instance Foo a => Bar a where
bar = foo @a
将在最后一行出现Not in scope: type variable 'a'
错误。如果删除类型应用程序,则会给出错误Could not deduce (Foo a0) from the context Foo a
,这是合理的,因为驴foo
本身是模棱两可的。
我是否可以通过某种方式访问类型参数,或者以其他方式强迫编译器识别此参数?
答案 0 :(得分:7)
类型变量可以在实例声明中使用,但前提是它是作用域:
{-# LANGUAGE FlexibleInstances, UndecidableInstances #-}
{-# LANGUAGE TypeApplications, AllowAmbiguousTypes #-}
{-# LANGUAGE ScopedTypeVariables, UnicodeSyntax #-}
class Foo a where foo :: String
class Bar b where bar :: String
instance ∀ a . Foo a => Bar a where
bar = foo @a
和往常一样,如果您更喜欢ASCII,也可以将∀
写入forall
。