What does “Clojure support multiple taxonomies” mean with respect to polymorphism?

I read the "Clojure Justification" here:

http://clojure.org/rationale 

In the Polymorphism section, he reads:

 Clojure multimethods decouple polymorphism from OO and types Supports multiple taxonomies Dispatches via static, dynamic or external properties, metadata, etc 

What is meant by "supporting multiple taxonomies" here? I am a fact, what is taxonomy in this case? Thanks

+6
source share
2 answers
 user> (defmulti shade :color) nil user> (defmethod shade :black [_] "darkest of darks") #<MultiFn clojure.lang.MultiFn@22b90f93 > user> (defmethod shade :white [_] "all frequencies are reflected") #<MultiFn clojure.lang.MultiFn@22b90f93 > user> (defmulti movement :legs) #'user/movement user> (defmethod movement 2 [_] "walks on hind legs") #<MultiFn clojure.lang.MultiFn@13b58075 > user> (defmethod movement 4 [_] "proceeds on all fours") #<MultiFn clojure.lang.MultiFn@13b58075 > user> ((juxt movement shade) {:name "cat" :legs 4 :color :black}) ["proceeds on all fours" "darkest of darks"] 

In the above code, two organization systems are created - one in terms of color, the other in terms of legs. Both of these taxonomies are equally valid, and the same object can fall into different places depending on the taxonomy used.

Multimethods can also use hierarchies to send (see derive and related functions), where each hierarchy can coexist in parallel (as opposed to a unified representation of the class hierarchy).

 user> (derive ::manx ::cat) nil user> (defmulti favorite-treat :species) #'user/favorite-treat user> (defmethod favorite-treat ::cat [_] "Tuna") #<MultiFn clojure.lang.MultiFn@264d27e6 > user> (derive ::indoor ::domestic) nil user> (defmulti activity :tameness) #'user/activity user> (defmethod activity ::domestic [_] "window watching") #<MultiFn clojure.lang.MultiFn@1654bf3f > user> ((juxt favorite-treat activity) {:species ::manx :tameness ::indoor}) ["Tuna" "window watching"] 

here the same kitten is a member of two hierarchies - one of domestication, and the other of genetics, and may have its own methods, allowed either in the appropriate way.

In addition, even if you install asid multimethods, relations created using derive support multiple inheritance, unlike the heirarchy Clojure class jvm, built on:

 user> (derive ::foo ::bar) nil user> (derive ::foo ::baz) nil user> (derive ::quux ::foo) nil user> (isa? ::quux ::foo) true user> (isa? ::quux ::bar) true user> (isa? ::quux ::baz) true user> (isa? ::bar ::baz) false 
+5
source

Clojure, like many other functional languages, uses free typing to provide simple ways to implement parametric polymorphism . This basically means that one method can be constructed in such a way that it does not care about the types of values ​​that are given to it.

Take, for example, the concat method. It takes any number of arguments of different forms and puts them on one list:

 user=> (concat [:a :b] nil [1 [2 3] 4]) (:a :b 1 [2 3] 4) 

Since it is not necessary to declare input of parameters for the arguments, concat can be written in such a way that you can provide an argument of any type (vector, function, keyword, string, etc.), and it will act on them in a similar way.

Clojure multimethods allows you to support this concept on Java objects, which can be completely different structures (i.e. taxonomies), using metadata or other properties to determine the appropriate way to deal with this argument. See the following example (taken from defmulti ):

 (defmulti greeting (fn[x] (x "language"))) (defmethod greeting "English" [params] (str "Hello! " (params "id"))) (defmethod greeting "French" [params] (str "Bonjour! " (params "id"))) =>(greeting {"id" "1", "language" "English"}) "Hello! 1" =>(greeting {"id" "2", "language" "French"}) "Bounjour! 2" 

The greeting method returns the value "language" from the card that matches the "English" or "French" method, which returns the correct corresponding value. I hope you can see how this concept could potentially be applied to almost any type of data or structure of objects. This powerful polymorphism idea is what Clojure developers are trying to show on the rationale page.

+3
source

Source: https://habr.com/ru/post/975204/


All Articles