Allgemeiner bezieht sich diese Frage auf verschiedene Ansätze zur expression problem. Die Idee ist, dass Ihr Programm eine Kombination aus einem Datentyp und Operationen darüber ist. Wir möchten in der Lage sein, neue Fälle hinzuzufügen, ohne die alten Klassen neu zu kompilieren.Aus welchen Gründen sind Protokolle und Multimethoden in Clojure weniger leistungsfähig für Polymorphie als Typklassen in Haskell?
Jetzt hat Haskell einige wirklich tolle Lösungen für die expression problem mit der TypeClass. Insbesondere - können wir tun:
class Eq a where
(==) :: a -> a -> Bool
(/=) :: a -> a -> Bool
member :: (Eq a) => a -> [a] -> Bool
member y [] = False
member y (x:xs) = (x == y) || member y xs
Jetzt in Clojure dort multimethods sind - so können Sie tun:
(defmulti area :Shape)
(defn rect [wd ht] {:Shape :Rect :wd wd :ht ht})
(defn circle [radius] {:Shape :Circle :radius radius})
(defmethod area :Rect [r]
(* (:wd r) (:ht r)))
(defmethod area :Circle [c]
(* (. Math PI) (* (:radius c) (:radius c))))
(defmethod area :default [x] :oops)
(def r (rect 4 13))
(def c (circle 12))
(area r)
-> 52
(area c)
-> 452.3893421169302
(area {})
-> :oops
Auch in Clojure Sie haben protocols - mit denen Sie tun können:
(defprotocol P
(foo [x])
(bar-me [x] [x y]))
(deftype Foo [a b c]
P
(foo [x] a)
(bar-me [x] b)
(bar-me [x y] (+ c y)))
(bar-me (Foo. 1 2 3) 42)
=> 45
(foo
(let [x 42]
(reify P
(foo [this] 17)
(bar-me [this] x)
(bar-me [this y] x))))
=> 17
Jetzt
this individual makes the claim:
Aber es gibt Protokolle und Multi-Methoden. Diese sind sehr mächtig, aber nicht so mächtig wie Haskells Typklassen. Sie können etwas wie eine Typklasse einführen, indem Sie Ihren Vertrag in einem Protokoll angeben. Dies geschieht nur beim ersten Argument, während Haskell die gesamte Signatur einschließlich des Rückgabewertes versenden kann. Multi-Methoden sind leistungsfähiger als Protokolle, aber nicht so leistungsfähig wie Haskells Versand.
Meine Frage ist: Was die Gründe sind, die Protokolle und Multimethoden in Clojure sind weniger leistungsfähig für Polymorphismus als typeclasses in Haskell?
Problem: "Ich möchte nicht unnötig einschränken, welche Art von Daten mein Code verarbeitet." ... "Ich weiß, ich werde dynamisches Tippen verwenden." Jetzt hast du acht Probleme. ;) – AndrewC
@AndrewC Anstiftung zur religiösen Debatte über das Tippen ist nicht notwendig. Es gibt Vorteile für beide, egal auf welcher Seite des Arguments Sie stehen. –
@ A.Webb OK vielleicht wäre es fairer zu sagen, dass statische Typisierung mit parametrischen Polymorphie und Typ Klassen wählt, um dieses Problem zur Kompilierzeit zu lösen, während dynamische Typisierung wählt, um dieses Problem zur Laufzeit zu lösen. – AndrewC