覆盖诸如“+”之类的方法的正确方法是什么?现在我有clojure - 本地覆盖运算符(例如“+”,“*”等)的正确方法
(defn- + [x y] (replacement x y))
但这会在命令行中产生警告。
WARNING: + already refers to: #'clojure.core/+ in namespace: <MY-NAMESPACE>, being replaced by #'<MY-NAMESPACE>/+
覆盖诸如“+”之类的方法的正确方法是什么?现在我有clojure - 本地覆盖运算符(例如“+”,“*”等)的正确方法
(defn- + [x y] (replacement x y))
但这会在命令行中产生警告。
WARNING: + already refers to: #'clojure.core/+ in namespace: <MY-NAMESPACE>, being replaced by #'<MY-NAMESPACE>/+
你需要排除由核心导入功能:
(ns your-ns
(:refer-clojure :exclude [+ ...]))
(defn + ...)
您确定要这样吗?如果是的话,你可以使用defprotocol来指定你想要覆盖的操作符,并扩展你希望实现这些覆盖的类。对于(人为)例如看到我answer to this question.
是的,我确定,我正在尝试编写DSL。好的解决方案,谢谢! – gatoatigrado
虽然我不建议重写核心功能,如+,你可以使用绑定或者让这一点,它取决于你想要什么样的行为:
(let [+ -] (reduce + [1 2 3])) ; -4
(defn my-plus [x] (reduce + x))
(let [+ -] (my-plus [1 2 3])) ;6
(binding [+ -] (my-plus [1 2 3])); -4
像在下面的评论中已经说过了,自从clojure 1.3以来,绑定不再起作用,因为var应该是动态的,而+, - 等不是。
出于测试目的/嘲笑,你可能会得到类似的行为。在这种情况下,看看有-redefs(因为Clojure的1.3): http://clojuredocs.org/clojure_core/clojure.core/with-redefs
您还可以覆盖内置在使用通用接口从contrib请算术,看到一个简单的例子如下,
http://nakkaya.com/2010/08/02/using-clojure-contrib-generic-interfaces/
对于Clojure的新手来说,这个问题不是关于面向对象意义上的'重写'(Clojure不是面向对象的)。真正问题在于如何防止警告当全局变量反弹时触发。第一个绑定发生是因为使用'ns'宏引入了clojure.core的映射。 (请参阅http://clojure.org/namespaces)当本地文件重新绑定var时,会发生第二次绑定。 –
另外,更多术语:Clojure没有方法。它有功能。 –