2010-02-05 3 views
22

Il semble que je rencontre des problèmes pour accéder à Integer.parseInt dans comp. Je peux accéder normalement comme ceci:Comment passer une méthode statique à comp dans clojure?

user=> (Integer/parseInt "123") 
123 

Mais si je le mets en comp, je reçois une erreur:

user=> (def vect-to-int (comp Integer/parseInt (partial apply str))) 
java.lang.Exception: Unable to find static field: parseInt in class java.lang.Integer (NO_SOURCE_FILE:3) 

Il me semble qu'il essaie de trouver un champ entier quand il devrait être à la recherche d'une méthode. Comment puis-je utiliser Integer.parseInt comme ça? Et est-il un meilleur moyen de convertir un vecteur de caractères en un int?

Répondre

26

Les fonctions Clojure sont des méthodes java mais les méthodes java ne sont pas des fonctions clojure Par exemple, les fonctions Clojure ont des méta-données et autres. Si vous voulez utiliser une méthode java où une fonction Clojure est appelée, vous avez deux choix pour l'encapsuler, memfn et fun or #() memfn est une fonction obsolète qui a enveloppé une méthode java dans une fonction clojure (il est bon de savoir qu'elle existe même si ce n'est pas souvent utilisé). La façon généralement accepté de conclure des méthodes Java est:

#(. instance method arg1 argN) 

ou pour les méthodes statiques

#(Class/MethodName arg1 argN) 
+0

Je suppose que la première ligne n'est pas tout à fait vrai que cela devient vraiment le point sur :) –

7
(def vec-to-int (comp #(Integer/parseInt %) (partial apply str))) 

Ou

(def vec-to-int #(Integer/parseInt (apply str %))) 

partial et comp sont généralement pas aussi succinct que l'utilisation Clojure #() pour faire une note de bas anonyme. Personnellement, je l'écrire de cette façon:

(defn vec-to-int [x] (Integer/parseInt (apply str x))) 

Vous pouvez le faire avec def simple, mais que gagnons-vous à l'aide def au lieu de defn, vraiment? L'utilisation de def masque le fait que vous définissez une fonction. defn met également en place des métadonnées supplémentaires pour vous (arglists) que def ne fait pas.

En tout cas, cela est une manière plus générale de faire ce que vous faites:

(def vec-to-int #(bigint (apply str %))) 

Et encore plus général:

(def vec-to-int #(read-string (apply str %))) 

Cela dépend si vous voulez être en mesure de gérer choses autres que les entiers.

Questions connexes