我为什么要使用“应用” Clojure中?(Why should I use 'apply&

2019-07-31 20:43发布

这是富希基在博客文章中一说,但我不明白,在使用应用的动机。 请帮忙。

Clojure的和CL之间有很大的区别是,Clojure是一个Lisp-1,所以不需要funcall,并申请仅用于一个功能应用到的参数运行时定义的集合。 因此,(申请F [i])可以写成(FI)。

此外,什么是他的“Clojure是Lisp的-1”和不需要funcall是什么意思? 我从来没有在CL编程。

谢谢

Answer 1:

你会使用申请 ,如果参数的数目传递给函数在编译时不知道(对不起,不知道Clojure的语法那么好,诉诸计划):

(define (call-other-1 func arg) (func arg))
(define (call-other-2 func arg1 arg2) (func arg1 arg2))

只要参数的数量是在编译时已知,你可以在上面的例子中进行直接通过他们。 但是,如果参数的数量不是在编译时知道,你不能做到这一点(当然,你可以尝试像):

(define (call-other-n func . args)
   (case (length args)
      ((0) (other))
      ((1) (other (car args)))
      ((2) (other (car args) (cadr args)))
      ...))

但是这变成了一场噩梦很快。 这就是申请进入图片:

(define (call-other-n func . args)
   (apply other args))

它需要什么都包含在给出最后一个参数给它的名单数量的参数,并呼吁与这些值应用于第一个参数传递的功能。



Answer 2:

Lisp的-1和术语Lisp的-2指的是函数是否在相同的命名空间变量。

在一个Lisp-2(即,2名的命名空间)中,在表格中的第一项将被评估为函数名 - 即使它实际上是与函数值的变量的名称。 所以,如果你要调用一个变量功能,您必须将变量传递给另一个函数。

在一个Lisp-1,如计划和Clojure的,计算结果为函数的变量可以去在初始位置,这样你就不需要使用apply ,以评估它的功能。



Answer 3:

apply基本解开一个序列和功能适用于它们作为单独的参数。

下面是一个例子:

(apply + [1 2 3 4 5])

返回15.基本上膨胀至(+ 1 2 3 4 5)而不是(+ [1 2 3 4 5])



Answer 4:

您可以使用apply来转换几个变量工作到一个对参数单个序列工作的功能。 您还可以在序列之前插入参数。 例如, map可以在几个序列工作。 该示例(从ClojureDocs )使用map转置矩阵。

user=> (apply map vector [[:a :b] [:c :d]])
([:a :c] [:b :d])

在一个插入此处的说法是vector 。 因此, apply膨胀到

user=> (map vector [:a :b] [:c :d])

可爱!

PS要返回载体,而不是向量序列的载体,包装在整个事情vec

user=> (vec (apply map vector [[:a :b] [:c :d]]))

虽然我们在这里, vec可以被定义为(partial apply vector) ,但事实并非如此。

关于Lisp的-1和Lisp-2:1和2表示的事物的名称可以在给定的上下文表示的数目。 在一个Lisp-2,你可以有两种不同的东西(函数和变量)具有相同的名称。 所以,无论是地方可能是有效的,你需要的东西来指示你的意思来装饰你的程序。 值得庆幸的是,Clojure的(或计划...)允许一个名称来表示的只有一件事,所以没有这样的装饰是必要的。



Answer 5:

对于应用型业务的通常模式是在运行时用一组参数,同上提供的功能相结合。

我没有做足够使用Clojure能够成为信心的微妙之处针对特定的语言,告诉使用的是否在这种情况下应用将是绝对必要的。



Answer 6:

应用与协议有用的,尤其是在线程宏一起。 我刚刚发现这一点。 既然你不能使用与宏在编译时扩展接口参数 ,你可以申请一个不可预知的大小,而不是载体。

所以我用这个,例如,作为持股约一个特定的XML文件和文件本身的一些元数据记录之间的接口的一部分。

(query-tree [this forms]
  (apply xml-> (text-id-to-tree this) forms)))

text-id-to-tree是一个分析文件到一个XML拉链这个特定记录的另一种方法。 在另一个文件中,我延伸以实现特定查询协议query-tree ,指定的命令的链通过XML->宏是有螺纹的:

(tags-with-attrs [this]
  (query-tree this [zf/descendants zip/node (fn [node] [(map #(% node) [:tag :attrs])])])

(注:此查询本身会返回大量的对于没有属性的标签“无”结果中过滤和减少唯一值的清洁列表)。

ZF,顺便说一下,是指clojure.contrib.zip过滤器,和zip到clojure.zip。 该XML->宏是从clojure.contrib.zip-filter.xml库,我:use



文章来源: Why should I use 'apply' in Clojure?
标签: lisp clojure