a 在数据类型声明中代表什么?

What does a stand for in a data type declaration?

通常在使用类型声明时我们会这样做:

function_name :: Type -> Type

但是在我试图解决的练习中有以下结构:

function_name :: Type a -> Type a

或在练习中明确说明

alphabet :: DFA a -> Alphabet a
alphabet = undefined

a 代表什么?

简答:这是一个类型变量。

在计算层面,我们定义函数的方式是使用变量来引用它们的参数。像这样:

f x = x + 3

这里x是一个变量,它的值会在函数调用的时候选择。 Haskell 在其类型子语言中具有相似(但不完全相同...)的机制。例如,您可以这样写:

type F x = (x, Int, x)
type Endo a = a -> a -> a

这里再次 x 是第一个变量(和 a 第二个变量),其值将在使用地点选择。定义新类型时也可以使用这一机制。 (前两个示例只是为现有类型赋予新名称,但以下示例做的更多。)最基本的重要示例之一是 Maybe 类型族:

data Maybe a = Nothing | Just a

= 右边的东西是计算级别的,所以你现在可以忽略它们,但在左边我们声明了一个新的类型家族 Maybe 它接受其他类型作为参数。例如Maybe IntMaybe (Bool, String)Maybe (Endo Char),甚至传入有变量的表达式Maybe (x, Int, x)都是可以的。

在句法上,类型构造函数(定义为程序文本的一部分并且我们希望编译器查找其定义的事物)以大写字母和类型变量(稍后将实例化的事物和所以目前没有具体的定义)以小写字母开头。

因此,在您显示的类型签名中:

alphabet :: DFA a -> Alphabet a

我怀疑实际上有 两个 构造对您来说是新的,而不仅仅是一个:首先,您询问的类型变量 a,其次,概念类型应用程序,我们在类型级别将一种“类函数”类型应用于另一种类型。 (在这个答案之外,人们说“参数化”而不是“类函数”。)

...而且,不管你信不信,甚至还有一个类型系统可以确保你不会写这样的东西:

Int a -- Int is not parameterized, so shouldn't be applied to arguments
Int Char -- ditto
Maybe -> String -- Maybe is parameterized, so should be applied to
                -- arguments, but isn't