Quelle est la différence entre doseq et for in Clojure? Quels sont quelques exemples de cas où vous choisiriez d'utiliser l'un plutôt que l'autre?
105
La différence est que for
construit une séquence paresseuse et la renvoie tandis que doseq
c'est pour exécuter des effets secondaires et renvoie nil.
user=> (for [x [1 2 3]] (+ x 5))
(6 7 8)
user=> (doseq [x [1 2 3]] (+ x 5))
nil
user=> (doseq [x [1 2 3]] (println x))
1
2
3
nil
Si vous souhaitez créer une nouvelle séquence basée sur d'autres séquences, utilisez pour. Si vous voulez faire des effets secondaires (impression, écriture dans une base de données, lancement d'une ogive nucléaire, etc.) basés sur des éléments de certaines séquences, utilisez doseq.
Notez également qu'il
doseq
est impatient pendant qu'ilfor
est paresseux. L'exemple manquant dans la réponse de Rayne estAu REPL, cela fera généralement ce que vous voulez, mais c'est essentiellement une coïncidence: le REPL force la séquence paresseuse produite par
for
, provoquant l'apparition des printlns. Dans un environnement non interactif, rien ne sera jamais imprimé. Vous pouvez voir cela en action en comparant les résultats deParce que le
def
formulaire renvoie la nouvelle var créée, et non la valeur qui lui est liée, il n'y a rien à afficher pour le REPL, etlazy
se référera à un lazy-seq non réalisé: aucun de ses éléments n'a été calculé du tout.eager
fera référence ànil
, et toute son impression aura été effectuée.la source