类型同义词的类型类实例

Posted

技术标签:

【中文标题】类型同义词的类型类实例【英文标题】:Typeclass instance for type synonym 【发布时间】:2015-11-15 17:53:58 【问题描述】:

恐怕我严重误解了 Haskell 中的类型。我会进入它。假设我定义了一个类型:

type Vector = [Num a]

所以我在同义词的定义中使用了一个类型类。然后,如果我想将它添加到另一个类型类,比如 Eq,也许我会这样做:

instance Eq Vector a where
  [] == [] = True
  [_]== [] = False
  [] == [_] = False
  (a : u) == (b : v) = (a == b) && (u == v)

但是当我这样做时,GHC 给出了一个

输入'['解析错误

它指的是[_]== [] = False行中的第一个左括号。

这是由我的类型定义问题引起的吗?

【问题讨论】:

您复制到问题中的内容是否有错字或遗漏?我不相信你有type Vector = [Num a],因为类型变量a 不存在。如果你这样做了,Num 类型是什么?它不能是基类中的 Num 类,因为这是一个约束,而不是一个类型。 如果Vector a 是一个定义为列表[F a] 的类型同义词,你为什么要为它编写一个Eq 实例? Eq a => Eq [a] 已经有一个 Eq 实例。 @AndreyChernyakhovskiy 我的 7.10 GHCi 对象 type Vector a = [Num a] 出现错误 Expected kind '*', but 'Num a' has kind 'Constraint',即使启用了 PolyKindsDataKinds 也不足为奇。 @Cirdec,我的是 7.6.3。看起来已经修复了一个错误。 顺便说一句,如果我没记错的话,不能在类型同义词上定义类型类的实例。 【参考方案1】:

此代码存在多个问题,导致无法对其进行编译。我认为您的意思是 Vector 由它包含的 a 类型参数化:

type Vector a = [a]

我已经删除了Num 约束,因为示例的其余部分不需要它;最后我会捡起来的。

列表已经有一个Eq 实例,所以这有点死胡同。一种前进的方式是切换到新类型:

newtype Vector a = Vector [a]

与使用type 声明的类型同义词不同,Haskell 将newtype 视为完全不同的类型。 Vector 不是一个列表,所以我们可以定义我们想要的任何类型的类实例。

我们的Eq 实例变长了一些,因为我们每次都必须编写Vector 构造函数。我在第一行的Vector a 周围添加了括号。

我们需要做的唯一其他更改是在实例之前添加Eq a 约束。在定义的最后一行,我们比较了两个Vectors 的第一个元素。这仅在a 类型是Eq 的实例时才有意义。

instance Eq a => Eq (Vector a) where
  Vector [] == Vector [] = True
  Vector [_] == Vector [] = False
  Vector [] == Vector [_] = False
  Vector (a : u) == Vector (b : v) = (a == b) && (Vector u == Vector v)

这样编译。您可以添加一个Num 约束,坚持除非aNum,否则没有人可以构造Vector a,或者如果aNum,则Vector a 只是Eq。如果这是您想做的事情,我可以添加一个示例。

【讨论】:

不要添加错误代码的示例。此类限制几年前就已经取消了。 @dfeuer,这是对我给出的例子的批评,还是只是对我最后一段的回应?如果是后者 - 是的,我把它省略了,因为这是一种不好的做法。 @bergey 很抱歉提出一个旧帖子,但我对学习 Haskell 很感兴趣。为了确保Vector 只能包含作为Num 实例的类型,量化类型可以吗? data Vector a = forall a . Num a => Vector [a]?还是有更“直接”的方式来做到这一点? @StevenL。我认为你会更好地为你的帖子提出一个新问题。如果你解释你正在尝试做的更广泛的背景,你会得到更好的答案。你想允许和禁止什么?你提议的类型没有做你想做的事,但不知道你想要什么什么我不知道还有什么建议。

以上是关于类型同义词的类型类实例的主要内容,如果未能解决你的问题,请参考以下文章

7.2类和类型

Python/Django:数据库模型中字段“类型”的同义词(保留的内置符号)

Thinking In Java 读书笔记

oracle中啥是同义词,它有几种类型,不同类型同义词的区别是啥?并写出语法?

Haskell 术语:类型与数据类型的含义,它们是同义词吗?

让Haskell区分类型同义词