map接受一个函数和一个列表,并将该函数应用于列表的每个元素。如,
(map f [x1 x2 x3])
;= [(f x1) (f x2) (f x3)]
数学上,列表是自然数ℕ的部分函数。如果 x :ℕ→ X 是某个列表, f : X → Y 是某个函数,然后map将对( f , x )带到列表f○x:ℕ→ Y 。因此,map和comp返回相同的值,至少在简单的情况下。
然而,当我们应用具有多个参数的地图时,会发生更复杂的事情。考虑一下这个例子:
(map f [x1 x2 x3] [y1 y2 y3])
;= [(f x1 y1) (f x2 y2) (f x3 y3)]
在这里,我们有两个列表 x :ℕ→ X 和 y :ℕ→ Y 相同的域,以及 f 类型的函数: X →( Y → Z )。为了评估元组( f , x , y ),地图必须在幕后做更多的工作。
首先,map构造对角线产品列表diag( x , y ):ℕ→ X × Y ,由diag定义( x , y )(n)=( x (n), y (N))。
其次,地图不会影响咖喱 -1 ( f ): X × Y →< EM>ž。最后,map组成这些操作以获得curry -1 (f)○diag( x , y ):ℕ→ Z < / em>的
我的问题是:这种模式是否概括?也就是说,假设我们有三个列表 x :ℕ→ X , y :ℕ→ Y 和 z :ℕ→ Z ,函数 f : X →( Y →( Z → W )))。 map是否将元组( f , x , y , z )发送到列表curry - 2 (f)○diag( x , y , z ):ℕ→ W ?
答案 0 :(得分:6)
问题标题似乎与身体中实际提出的问题没什么关系;我会尝试解决这两个问题。
正如(map inc [1 2 3])
和(comp inc [1 2 3])
等示例所证明的那样 - 顺便提一下,这两者在Clojure中都非常有意义 - Clojure函数map
和comp
完全可以运行即使在一个序列情况下也是如此。 map
根本不会将其序列参数视为可调用对象的软件意义上的函数,而comp
以这种方式处理其所有参数; map
返回复合数据,而comp
则不返回; comp
返回的值可以作为函数调用,而map
的返回值不是;等
(其他函数语言类似地具有单独的“map”和“compose”高阶函数;在Haskell中,这些是map
(以及更一般的fmap
)和(.)
。 )
值得注意的是,map
没有对其输入函数执行任何实际内存中的参数化,也不会对输入函数应用任何deschönfinkelizing/ uncurrying转换。
模式确实很好地概括了,但是值得注意的是,什么是什么等等的功能 - 在模型的引擎盖下,就像它一样 - 取决于表示的选择,这往往是任意的。有限序列可以很好地表示为(全部)函数,有限的序数作为域,或者作为Kuratowski元组,或者你描述的方式,你不关心你的列表不一定是“无间隙”等等。取决于表示选择,自然数的概念可能根本不会进入图片,表示列表的对象可能看起来像或者看起来不像其codomain是列表条目集等的超集的函数。
答案 1 :(得分:3)
我不知道它是否有帮助,但是:
答案 2 :(得分:1)
技术上是的,map可以被视为这样的组合函数,尽管在实践中它引入了一些comp没有的开销。
map
生成一个延迟序列,在最终读取结果时将计算序列。所以它返回的序列不是严格意义上的类型表达式所暗示的结果。它还增加了序列的开销并改变了评估顺序,因为它是懒惰和分块的。