[因答案中缺少#而编辑]
走这条路线有些麻烦,因为constantly
的目的是允许一个任意参数的多参数函数总是返回一个常量。#(...)匿名函数简写提供了快速定义匿名函数的方法
0 - #(vector)
1- #(vector %1)
2 - #(vector %1 %2)
...
n - #(vector %1 %2 ... %n)
& args - #(apply vector %&)
不过有一些限制,因为您正在定义函数体...如果您尝试定义一些像identity这样的东西,它最终会看起来像一次调用...
#(%)
;;这将尝试将单参数作为一元函数调用。
一种解决办法是将输入绑定到一个let或某种形式中,以传达参数个数...
#(let [v %] v)
或者
#(do %)
将像identity一样工作,我们只需在体中返回它即可。
我们想要定义一个带可变参数的函数,因此我们想用 %& 来表示参数。然而,对于结果来说,这些参数毫无意义……它们唯一的用途就是向匿名函数糖(sugar)传达参数的数量或参数的个数。
虽然有点不自然,但这确实是一种可行的方法。
(defn constantly2 [v]
;;ignore the arguments, but communicate a varargs function
#(let [_ %&]
v))
user=> (def f (constantly2 10))
#'user/f
user=> (f 1 2 3 4)
10
user=> (f 1)
10
user=> (f 5)
10
user=> (f :a)
10
我可能会尽量避免使用 #(..) 的语法糖来完成这种类型的事情。这种简写对于非常简单的内联匿名函数来说最有用,即便如此,我也通常更喜欢明确地写出 fn
。