请在 Clojure 2024 状况调查 中分享您的想法!

欢迎!请查阅 关于 页面了解更多有关本站的信息。

0 投票
Clojure

考虑这个例子

`
user=> (defprotocol Foo (foo [x] x))
Foo
user=> (defrecord Bar [gaz waka] Foo)
user.Bar
user=> (def bar (Bar. 1 2))

'user/bar

user=> (.foo bar)

AbstractMethodError user.Bar.foo()Ljava/lang/Object; sun.reflect.NativeMethodAccessorImpl.invoke0 (NativeMethodAccessorImpl.java:-2)
user=>
`

默认实现怎么办。

4 答案

0 投票

评论由:mobiusinversion 发布

按照目前的情况,你需要用这个方法做绕过

http://stackoverflow.com/questions/15039431/clojure-mix-protocol-default-implementation-with-custom-implementation

0 投票

评论由:wagjo 发布

我认为我们不需要它。为什么扩展一个协议但不实现其方法,然后调用这些方法并期望它们不抛出异常?明确您的类型应该做什么,无论是默认行为还是自定义行为。您基本上有三个选择

`
(defn default-foo
[this]
:foo)

(defprotocol P
(-foo [this]))

(deftype T
P
(-foo [this] (default-foo))

(defn foo
[x]
(-foo x))
`

或者

`
(defprotocol P
(-foo [this]))

(deftype T)

(defn foo
[x]
(if (satisfies? P x)

(-foo x)
:foo))

`

或者

`
(defprotocol P
(-foo [this]))

(extend-protocol P
java.lang.Object
(-foo [this] :foo))

(deftype T)

(defn foo
[x]
(-foo x))
`

我认为第一个方法不符合 Clojure 的风格,您应该更喜欢后两种方法。

0 投票

评论由:mobiusinversion 发布

我同意,这是一个低优先级的增强。我认为这可以使协议体验更加DWIMy,Java 8已经为相同类型的便利在接口上提供了默认实现。

0 投票
参考:https://clojure.atlassian.net/browse/CLJ-1563(由 alex+import 报告)
...