Either类型构造函数是否包含左/右案例的幻像类型?

时间:2017-11-14 10:18:24

标签: haskell polymorphism higher-kinded-types type-constructor

AFAIK,只有类型存在于Haskell中的值,而不是类型构造函数。 Either是类* -> * -> *的二进制类型构造函数。 LeftRight都将此类型构造函数应用于单个类型,该类型由传递的值提供。这是否意味着在两种情况下Either仅部分应用,因此仍然是一个等待缺失类型参数的类型构造函数?

let x = Right 'x' -- Either a Char

x的类型为Either a Char。我认为这种类型会有* -> *种。这显然是多态类型,而不是基础类型。然而Either a Char可以居住'x'等值。

我怀疑类型变量aRight案例的幻像类型。 b Left。我知道与Const相关的幻像类型,其中根本没有使用相应的类型变量。我是正确的大头钉吗?

3 个答案:

答案 0 :(得分:8)

  

AFAIK,只有类型存在于Haskell中的值,而不是类型构造函数。

专注于。

  

LeftRight都将此类型构造函数应用于单个类型

你不能这么说。 LeftRight根本不存在于类型语言中,因此它们不会对任何类型应用任何内容,它们仅适用于

  

x的类型为Either a Char。我认为这种类型会有* -> *

您需要区分函数/构造函数参数类型变量。它基本上是free and bound variables之间的区别。 Either a Char仍然有*,而不是* -> *,因为它已经应用于a。是的,这是一个类型变量,但它仍然是一个已经应用的参数。

  

然而Either a Char可以居住'x'等值。

不完全 - 它可以居住在像Right 'x'这样的值。

  

我怀疑类型变量aRight案例的幻像类型。 b

Left

有点,但我不会称之为“幽灵”,因为你不能只计算LeftRight。除非您选择Either Void b,否则至少不会,但在这种情况下,您没有a变量。

答案 1 :(得分:1)

我认为,当且仅当类型变量的选择不限制可以将哪些值传递给类型的构造函数时,类型变量才是幻像。重要的是这是一个以类型为中心的定义。它仅通过查看类型定义来确定,而不是根据类型的某个特定值来确定。

String中是否显示Left 5 :: Either Int String类型的值没有问题?一点也不。重要的是,StringEither Int String的选择会阻止Right ()进行类型检查。

答案 2 :(得分:1)

Haskell具有“隐式通用量化”,这意味着类型变量具有隐式forallEither a Int相当于forall a. Either a Int

考虑forall的一种方法是它就像一个lambda,但是对于类型变量。如果我们对类型应用程序使用语法@,那么,您可以“应用”一个类型并获取一个新类型。

let foo = Right 1 :: forall a. Either a Int
foo @Char   :: Either Char Int
foo @Double :: Either Double Int