3

如果这个问题有点含糊,请提前道歉。这是一些周末白日梦的结果。

借助 Haskell 出色的类型系统,将数学(尤其是代数)结构表达为类型类非常令人愉快。我的意思是,看看numeric-prelude!但是在实践中利用这种奇妙的字体结构对我来说总是很困难。

您有一种很好的类型系统方式来表达它,v1并且v2是向量空间的元素,并且是向量空间Vw元素W。类型系统允许您编写一个添加v1and的程序v2,但不能添加v1and w。伟大的!但在实践中,您可能想要使用可能有数百个向量空间,并且您当然不想创建类型V1V2...、V100并将它们声明为向量空间类型类的实例!或者,也许您从现实世界中读取了一些数据,从而产生了符号ab并且c-您可能想要表示这些符号上的自由向量空间确实是向量空间!

所以你被卡住了,对吧?为了在科学计算环境中做很多你想用向量空间做的事情,你必须放弃你的类型系统,先使用向量空间类型类,并让函数进行运行时兼容性检查。你应该这样做吗?难道不能利用 Haskell 是纯函数式的事实来编写一个程序来生成您需要的所有类型并将它们插入到实际程序中吗?这样的技术存在吗?一定要指出我是否只是在这里忽略了一些基本的东西(我可能是):-)

编辑:我刚刚发现fundeps。我将不得不考虑一下它们与我的问题的关系(对此有启发性的评论表示赞赏)。

4

2 回答 2

7

模板 Haskell允许这样做。wiki 页面有一些有用的链接;特别是Bulat 的 教程

顶级声明语法是您想要的。通过键入:

mkFoo = [d| data Foo = Foo Int |]

data Foo = Foo Int您生成一个模板 Haskell 拼接(如编译时函数),只需插入 line 即可创建声明$(mkFoo)

虽然这个小例子不太有用,但您可以向 mkFoo 提供一个参数来控制您想要多少不同的声明。现在 a$(mkFoo 100)将为您生成 100 个新的数据声明。您还可以使用 TH 生成类型类实例。我的自适应元组包是一个非常小的项目,它使用 Template Haskell 来做类似的事情。

另一种方法是使用Derive,它将自动派生类型类实例。如果您只需要实例,这可能会更简单。

于 2010-11-01T09:47:17.887 回答
5

Haskell 中还有一些简单的类型级编程技术。一个典型的例子如下:

-- A family of types for the natural numbers
data Zero
data Succ n

-- A family of vectors parameterized over the naturals (using GADTs extension)
data Vector :: * -> * -> * where
    -- empty is a vector with length zero
    Empty :: Vector Zero a
    -- given a vector of length n and an a, produce a vector of length n+1
    Cons  :: a -> Vector n a -> Vector (Succ n) a

-- A type-level adder for natural numbers (using TypeFamilies extension)
type family Plus n m :: *
type instance Plus Zero n = n
type instance Plus (Succ m) n = Succ (Plus m n)

-- Typesafe concatenation of vectors:
concatV :: Vector n a -> Vector m a -> Vector (Plus n m) a
concatV Empty ys = ys
concatV (Cons x xs) ys = Cons x (concatV xs ys)

花点时间接受它。我认为它的工作原理非常神奇。

然而,Haskell 中的类型级编程在功能上是不可思议的——足以引起人们对你不能做多少事情的注意。依赖类型的语言,如AgdaCoqEpigram将这种风格发挥到了极限和全部力量。

模板 Haskell 更像是通常的 LISP 宏风格的代码生成。你写一些代码来写一些代码,然后你说“ok insert that generated code here”。与上述技术不同,您可以通过这种方式编写任何可计算指定的代码,但您不会获得如上所示的非常通用的类型检查concatV

所以你有几个选择来做你想做的事。我认为元编程是一个非常有趣的领域,在某些方面还很年轻。尽情探索吧。:-)

于 2010-11-01T17:02:11.817 回答