Co jest złego w poniższym używaniu spoczynkowych params z defprotocol i defrecord w Clojure?Co jest złego w korzystaniu z par zabezpieczeń z defprotocol i defrecord w Clojure?
(defprotocol prot
(f [this] [this & rest]))
(defrecord rec []
prot
(f [this] "one arg")
(f [this & rest] "more than one arg"))
(prn (f (rec.)))
; (prn (f (rec.) 5))
(prn (f (rec.) 5 6))
; (prn (f (rec.) 5 6 7))
Powyższy kod drukuje wyjście Spodziewam:
"one arg"
"more than one arg"
Ale gdybym odkomentowaniu jeden z komentujących linii, otrzymuję poniższy wyjątek:
Exception in thread "main" java.lang.IllegalArgumentException: No single method: f of interface: user.prot found for function: f of protocol: prot (bug.clj:10)
at clojure.lang.Compiler.analyzeSeq(Compiler.java:5376)
at clojure.lang.Compiler.analyze(Compiler.java:5190)
at clojure.lang.Compiler.analyze(Compiler.java:5151)
at clojure.lang.Compiler$InvokeExpr.parse(Compiler.java:3057)
at clojure.lang.Compiler.analyzeSeq(Compiler.java:5371)
at clojure.lang.Compiler.analyze(Compiler.java:5190)
at clojure.lang.Compiler.analyze(Compiler.java:5151)
at clojure.lang.Compiler$BodyExpr$Parser.parse(Compiler.java:4670)
at clojure.lang.Compiler$FnMethod.parse(Compiler.java:4328)
at clojure.lang.Compiler$FnExpr.parse(Compiler.java:3173)
at clojure.lang.Compiler.analyzeSeq(Compiler.java:5367)
at clojure.lang.Compiler.analyze(Compiler.java:5190)
at clojure.lang.Compiler.eval(Compiler.java:5421)
at clojure.lang.Compiler.load(Compiler.java:5857)
at clojure.lang.RT.loadResourceScript(RT.java:340)
at clojure.lang.RT.loadResourceScript(RT.java:327)
at clojure.lang.RT.loadResourceScript(RT.java:319)
at clojure.main$load_script.invoke(main.clj:220)
at clojure.main$script_opt.invoke(main.clj:273)
at clojure.main$main.doInvoke(main.clj:354)
at clojure.lang.RestFn.invoke(RestFn.java:409)
at clojure.lang.Var.invoke(Var.java:365)
at clojure.lang.AFn.applyToHelper(AFn.java:163)
at clojure.lang.Var.applyTo(Var.java:482)
at clojure.main.main(main.java:37)
Caused by: java.lang.IllegalArgumentException: No single method: f of interface: user.prot found for function: f of protocol: prot
at clojure.lang.Compiler$InvokeExpr.<init>(Compiler.java:2880)
at clojure.lang.Compiler$InvokeExpr.parse(Compiler.java:3063)
at clojure.lang.Compiler.analyzeSeq(Compiler.java:5371)
... 24 more
dlaczego tak jest?
Wygląda na to, że funkcja wysyłania protokołów nie obsługuje funkcji z parametrami variadic. – Ankur
Możliwy duplikat [Do czynienia z protokołami clojure pozwala na stosowanie metody variadycznej w taki sam sposób jak w przypadku funkcji (przy użyciu znaku ampersand)?] (Http://stackoverflow.com/questions/5401378/do-clojure-protocols-allow-one-to -i-variadic-method-the-way-funcions-do-wi) – amalloy