2

AFAIK 没有办法在 Haskell 中做异构数组或扩展数据类型。然而,它似乎可以通过使用嵌套对轻松实现(就像 CONS 一样)。

例如

data Point2D a = Point2D a a
data Point3D a = Point3D a a a

可以像这样使用嵌套对编写;

type Point2D = (a, (a, ())
type Point3D = (a, (a, (a, ()))

这样访问器对于 Point2D 和 Point3D 来说是通用的

x = fst
y = fst.snd
z = fst.snd.snd

这种技术也可以用来扩展这样的记录

type Person = (String, ())
name = fst
type User = (String, (String, ())
email = fst.snd

ETC ...

这是一个好主意吗?如果是这样,为什么 Haskell 中没有对此类东西的内置支持?这是 GADT 的目的吗?

4

2 回答 2

4

如果这是您需要的,这可能是一个好主意。

GADT 与这个想法没有直接关系(如果您想了解更多关于 GADT 的信息,最好使用谷歌 GADT 并阅读一些链接,和/或询问单独的 Stackoverflow 问题)。

出于同样的原因,没有对图形、矩阵运算或大多数其他东西的内置支持。不需要内置支持,因为它可以通过库很好地添加,例如HList 包(实际上,即使“内置”到 Haskell 的大多数功能实际上也只是在库中实现;只是库碰巧总是与 Haskell 一起分发)。

HList 具有表示“异构列表”的花哨类型和对其执行操作的便捷功能,并且还使用这些来开发“可扩展记录”。HLists 基本上等同于您可以通过进一步开发嵌套元组的想法来做的事情,因此您的基本想法已经足够好,以至于有人已经想到了。:)

于 2014-03-23T11:09:23.577 回答
0

这是一种任意嵌套对的方法:

data Y f = In (f (Y f))
data P a = Pair Int a | STOP
type PY = Y P

a, b :: PY
a = In (Pair 23 (In (Pair 24 (In STOP))))
b = In (Pair 23 (In (Pair 24 (In (Pair 25 (In STOP))))))    
c = [a,b]   -- a and b have same type
于 2014-03-23T20:11:48.427 回答