我有使用重叠实例的以下
Haskell代码;我试图实现一个函数,它将函数的类型作为String生成,或者 – 更一般地说 – 对不同的函数类型执行不同的操作:
{-# OPTIONS_GHC -fglasgow-exts #-}
{-# LANGUAGE OverlappingInstances, IncoherentInstances #-}
module Test
where
data TypeString = MKTS String
instance Show TypeString where
show (MKTS s) = s
class ShowType b c where
theType :: (b -> c) -> TypeString
instance ShowType b b where
theType _ = MKTS "b -> b"
instance ShowType b c where
theType _ = MKTS "b -> c"
instance ShowType (b, b') c where
theType _ = MKTS "(b, b') -> c"
class Problem a where
showProblem :: a -> TypeString
instance Problem (b -> c) where
showProblem f = theType f
Haskell显示我输入时的预期行为
> theType (uncurry (+))
(b,b') -> c
但是:任何人都可以解释以下内容:
> showProblem (uncurry (+))
b -> c
…并解释,如何避免Haskell选择过于笼统的实例……
最佳答案 使用的问题的实例是针对b – >进行的. C.如果你看一下showProblem的签名,你会发现没有ShowType上下文.如果没有上下文,则编译器只能静态推断实例.因此,b – >的实例选择c,因为它是静态拟合的实例.
我不知道如何解决这个问题,恕我直言,它可以手工提供上下文,但我真的不知道:
class Problem a where
showProblem :: ShowType a => a -> TypeString
instance Problem (b -> c) where
showProblem :: ShoType (b -> c) => (b -> c) -> TypeString
showProblem = theType
对我来说,使用OverlappingInstances通常意味着我在我的代码中做了错误的设计决定.