我写了一个函数来计算两组的对称差异(4clojure站点上的一个问题).该函数通过了单元测试,但考虑到我有重复的代码,它并不像我想的那样干净.
(fn [x y] (set (concat
(keep-indexed #(if (nil? (get y %2)) %2) x)
(keep-indexed #(if (nil? (get x %2)) %2) y))))
Run Code Online (Sandbox Code Playgroud)
显然我更喜欢这样的东西:
(fn [x y] (set (concat (diff x y) (diff y x))))
Run Code Online (Sandbox Code Playgroud)
diff函数定义并引用"inline",但我不知道如何在一个fn块中执行此操作.
Mat*_*ick 23
使用let或letfn:
(fn [x y]
(let [diff (... function body here ...)]
(set
(concat (diff x y) (diff y x)))))
Run Code Online (Sandbox Code Playgroud)
Art*_*ldt 11
使Clojure成为lisp(以及一般的函数式语言)的一个特性是,函数是 Clojure 中的第一类东西,特别是它们是Object.当你使用(defn name [arg] ...)if 函数构建函数然后将它存储在var中时,你可以在程序的任何地方找到它.它很像这样:
(def name (fn [arg] ...))
Run Code Online (Sandbox Code Playgroud)
now name包含一个可以广泛访问的函数.函数不必存储在变量中,特别是如果它们仅在函数中需要.在这种情况下,将函数绑定到本地名称更有意义,就像Matt Fenwick的答案一样.
(let [name (fn [agr] ...)] ...)
Run Code Online (Sandbox Code Playgroud)
在letfn宏观使这更优雅.重要的是要了解功能是存储在物体中的对象,您可以选择适合您需要的容器.