提升和扩展的双重概念在 Haskell 中绝对被使用,也许最突出的是以共生的形式extend
和单子bind
。 (令人困惑的是,extend
是提升,而不是扩展。)comonadw
's extend
让我们取一个函数w a -> b
并把它举起来extract :: w b -> b
获取地图w a -> w b
。在 ASCII 艺术中,给出图表
w b
|
V
w a ---> b
其中垂直箭头是提取,extend
给我们一个对角箭头(使图表通勤):
-> w b
/ |
/ V
w a ---> b
大多数 Haskellers 更熟悉的是双重概念bind
(>>=
) 对于一个单子m
。给定一个函数a -> m b
and return :: a -> m a
,我们可以“扩展”我们的功能return
得到一个函数m a -> m b
。在 ASCII 艺术中:
a ---> m b
|
V
m a
gives us
a ---> m b
| __A
V /
m a
(That A
是一个箭头!)
So yes, extend
could have been called lift
, and bind
could have been called extend
. As for Haskell's lift
s, I have no idea why they're called that!
编辑:实际上,我再次认为,哈斯克尔lift
s 实际上是扩展。如果f
是适用的,我们有一个函数a -> b -> c
,我们可以用以下方式编写这个函数pure :: c -> f c
得到一个函数a -> b -> f c
。非柯里化,这与函数相同(a, b) -> f c
。现在我们也可以打(a, b)
with pure
得到一个函数(a, b) -> f (a, b)
。现在,由fmap
ing fst
and snd
,我们得到一个函数f (a, b) -> f a
and f (a, b) -> f b
,我们可以将其组合起来得到一个函数f (a, b) -> (f a, f b)
。与我们一起作曲pure
从之前给出(a, b) -> (f a, f b)
。唷!回顾一下,我们有 ASCII 艺术图
(a, b) ---> f c
|
V
(f a, f b)
Now liftA2
给我们一个函数(f a, f b) -> f c
,我不会画它,因为我厌倦了制作糟糕的图表。但重点是,该图是通勤的,所以liftA2
实际上给了我们水平箭头沿着垂直箭头的延伸。