2011-01-12 15 views
8

Clojure Meta wird nur beibehalten, wenn eine Funktion darauf achtet und die Clojure-Kernfunktionen Meta nicht global erhalten. Die allgemeine Faustregel, die ich gehört habe, ist, dass Sammlungsfunktionen wie conj, assoc usw. Metakonservierung erhalten sollen, aber Sequenzfunktionen wie map, filter, take usw. met nicht beibehalten.Welche Funktionen in Clojure Core erhalten Meta?

Gibt es irgendwo eine Liste von Funktionen, die Meta schützen?

Antwort

5

Es geht nur um die Typen. Sequenzfunktionen verhalten sich so, als würden sie seq auf ihrem Argument aufrufen und daher nicht immer den gleichen Objekttyp zurückgeben. Sammlungsfunktionen und typspezifische Funktionen rufen seq nicht auf und geben ein Objekt desselben Typs zurück, das ihnen übergeben wurde. Es gibt ihnen die Illusion, dasselbe Objekt zurückzugeben (dies könnte der Grund für dieses Verhalten sein), auch wenn das nicht der Fall ist. Wir können sagen, dass die Faustregel darin besteht, dass eine Funktion das Meta behält, wenn es den Typ bewahrt.

user> (meta (seq (with-meta (list 1) {:a 1}))) 
{:a 1} 
user> (meta (seq (with-meta (vector 1) {:a 1}))) 
nil 

Achten Sie darauf, sich bewusst sein, wenn Faulheit hart beteiligt: ​​

user> (type (list 1)) 
clojure.lang.PersistentList 
user> (type (map identity (list 1))) 
clojure.lang.LazySeq 
user> (meta (seq (with-meta (map identity (list 1)) {:a 1}))) 
nil 

Eine Liste der Funktionen, die Meta auf Sammlung bewahrt, die data structures Seite. Diejenigen, die Meta nicht beibehalten, befinden sich unter der sequences Seite mit der Ausnahme, wenn sie ein Objekt desselben Typs zurückgeben.

Unter der Haube bin ich nicht ganz sicher über die Details, da Faulheit und chunked Sequenz hinzugefügt wurde, aber Sie können seq und seqFrom Methoden suchen aus der RT Klasse an den cons. Die Funktionen, die Metadaten nicht beibehalten, durchlaufen diese Methoden. Während die Sammlungsfunktionen mit Methoden arbeiten, die für ihre Typen spezifisch sind.

Verwandte Themen