为什么在定义实例时会出现模糊的出现错误?

时间:2017-05-05 12:13:40

标签: haskell syntax typeclass

我有一个Foo类型,并希望将其设为Show的实例,以便我可以在GHCi中使用它:

data Foo = Foo

instance Show Foo where
show Foo = "Foo"

但是,当我尝试使用它时,出现了模糊的错误:

ghci> show Foo
<interactive>:4:1:
    Ambiguous occurrence `show'
    It could refer to either `Main.show', defined at Foo.hs:4:1
                          or `Prelude.show',
                             imported from `Prelude' at Foo.hs:1:1
                             (and originally defined in `GHC.Show')

为什么呢?我刚刚定义了属于类型类的函数,不是吗?

1 个答案:

答案 0 :(得分:6)

TL; DR:缩进您的实例绑定。

启用警告,您会注意到您没有实现实例操作 show,而是实现了具有相同名称的 new 函数:

Foo.hs:3:10: Warning:
    No explicit implementation for
      either `showsPrec' or `Prelude.show'
    In the instance declaration for `Show Foo'

因此现在有两个showMain.show(您刚刚意外定义的那个)和Prelude.show(您想要使用的类别之一)。

我们可以通过查看他们的类型来验证(虽然我们需要完全限定他们的名字):

ghci> :t Main.show
Main.show :: Foo -> [Char]
ghci> :t Prelude.show
Prelude.show :: Show a => a -> String

那是因为你的where绑定需要缩进,就像你在普通函数中缩进它们一样。即使只有一个空间就足够了:

instance Show Foo where
 show Foo = "Foo"

请记住,Haskell使用空格来分隔块。只要问问自己:where什么时候会停止?