精简版
我想要一个多元函数来调度 2 元版本的类型,但我希望 1 元版本在所有类型中都相同。
长版(带示例)
我有一个看起来像这样的协议
(defprotocol foo
(bar [d] [d x]))
如果我想要“TypeA”来扩展这个协议,那么我有以下
(extend-protocol foo
TypeA
(bar
([d] #(bar d %))
([d x] (TypeA-fn x))))
对于某些特定于 TypeA 的函数 TypeA-fn。
如果我想要“TypeB”来扩展这个协议,那么我有以下
(extend-protocol foo
TypeB
(bar
([d] #(bar d %))
([d x] (TypeB-fn x))))
对于某些特定于 TypeB 的函数 TypeB-fn。
我试图创造的效果是柯里化。
(bar instance-of-TypeA x)
是双重的,比如说,虽然
(bar instance-of-TypeA)
返回一个将 TypeA 映射到 double 的函数。
关键是 bar 的单参数实现总是相同的,而多参数实现取决于类型。自然,我不想每次为单参数版本扩展此协议时都重复自己,那么执行此操作的惯用 clojure 方法是什么。我考虑过不指定一个单一的 arity 版本,并在任何地方使用 (partial bar TypeX),但我厌倦了部分。
建议的解决方案 我可以将原始函数包装在一个新函数中,例如
(defprotocol foo
(bar-method [d x]))
(extend-protocol foo
TypeA
(bar-method
([d x] (TypeA-fn x))))
(defn bar
([d] (fn [x] (bar-method d x))
([d x] (bar-method d x))
但是为了一个目的而引入两个功能似乎不优雅。