Hom 函子 在第一个参数中是逆变的Hom(-,-)
,在第二个参数中是协变的。
这个事实能否以某种方式提供另一种解释,为什么 Scala 的Function1[-T1, +R]具有相同的属性?
例如,我在这里看到了这种说法,但是在应该解释这两个概念之间的联系的地方,有太多的挥手让我大吃一惊。
Hom 函子 在第一个参数中是逆变的Hom(-,-)
,在第二个参数中是协变的。
这个事实能否以某种方式提供另一种解释,为什么 Scala 的Function1[-T1, +R]具有相同的属性?
例如,我在这里看到了这种说法,但是在应该解释这两个概念之间的联系的地方,有太多的挥手让我大吃一惊。
Scala 类型有两类。
一种是通常的类型和函数类别,其中类型是对象,箭头是函数。
另一种是类型和子类型,其中类型是对象,子类型关系是箭头。这个类别是一个poset。
Scala 中的协变和逆变正是后一类中内函子的协变和逆变。
现在第二个类别恰好是第一个类别的子类别,因为投影箭头将子类型映射到超类型。第一类的这些箭头正是(所有)第二类的箭头。所以第一类的每个协变内函子自然(即通过自然变换)是第二类的协变内函子。
事实上,如果一个函子F
映射A
到A'
和B
到B'
,并且每个箭头都映射f: A -> B
到一个箭头f': A' -> B'
,并且如果A
是 的子类型B
,那么投影箭头prj_A,B
映射到投影箭头prj_A',B'
,如果存在,那么A'
是B
' 的子类型。关于逆变函子也是如此。
现在只剩下看到它Function1
在某种意义上是 Hom 函子了。事实上,如果我们将 Scala 类型视为其值的集合,那么它就是从toFunction1[A,B]
的一组态射(Scala 函数)。箭头映射由合成给出。并且由于它在第一类中是协变的(逆变),所以它在第二类中也必须是协变的(逆变)。A
B
编辑:更正了子类型/supertupe 混淆。
免责声明:我从未研究过范畴论。我可能知道也可能不知道我在说什么。
如果您对设置很小心,可能不会。Function1非常类似于 Hom 函子(的对象部分)——除了它的目标不是完全相同的类别。Function1 映射的目标是(子类别)scala
具有 Scala 类型作为对象和函数作为箭头的类别;而 Hom 函子的目标是 SET(的子类别)。他们的图像可能是同构的,但尚不清楚将两个函子和同构结合起来是否以您需要的方式保留结构,以便在整个链中保留方差。