【问题标题】:Haskell, Instance, Type ConstraintsHaskell,实例,类型约束
【发布时间】:2015-09-06 22:09:36
【问题描述】:

我在 Haskell 中创建了一个新类 Eqa

class Eqa a where

   (=~) :: a -> a -> Bool

   (/~) :: a -> a -> Bool

并且想要定义 (=~) 与 Prelude 中的 (==) 相同。所以我尝试了

instance Eqa Int where            
   x=~y = x==y

   x/~y = x/=y

但这仅适用于Int(当然)。 如何更改我的代码以使其适用于所有数字类型?

【问题讨论】:

  • 如何更改我的代码以使其适用于所有数字类型?“this”在您的句子中到底指的是什么?
  • 使用我定义的实例,我只能比较 Int 的类型,但我想比较所有数字类型,即 float、Integer、...
  • 这不是你能真正做到的。 Num 类型类不提供(==)。您可以说服 GHC 接受具有正确语言编译指示的 instance Num a => Eqa a 的定义,但这很荒谬,实际上您将无法使用它。

标签: haskell types constraints instance


【解决方案1】:

您所要做的就是将a 绑定到Num a

instance Num a => Eqa a where            
    x=~y = x==y
    x/~y = x/=y

如需更多信息,请查看Numeric Types subsection of Real World Haskell 以了解与每种数值类型相关的类。

【讨论】:

  • 这不是一个很好的解决方案。首先,它不像写的那样工作:它需要FlexibleInstancesUndecidableInstances;另外,在现代 GHC 中,Eq 不再是 Num 的超类,因此您也需要一个 Eq a 约束。更重要的是,它使得定义Eqa 的其他实例相当麻烦:如果我们添加instance Eqa () where { _ =~ _ = True ; _ /~ _ = False },那么() =~ () 会给我们一个“重叠实例”错误,因为() 可以 Num 实例!
  • @AntalS-Z 你是否知道Eq 何时(即,对于哪个版本的 GHC)不再是 Num 的超类?
  • @Jubobs:从 GHC 7.4.1 开始。这里是the GHC 7.4.1 release notes,上面写着“Num 类不再有EqShow 超类”;比较the GHC 7.2.1 release notes,它什么也没说。这是从Ben James's answerexactly this question
  • @AntalS-Z 非常感谢。谢谢。
【解决方案2】:

为什么不直接写

(=~) :: Num a => a -> a -> Bool
x=~y = x==y

如果你实际上并不需要不同类型的代码不同,那你为什么还需要一个类呢?

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 2012-03-21
    • 2014-10-02
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2018-06-15
    • 1970-01-01
    • 2012-09-06
    相关资源
    最近更新 更多