2017-05-08 2 views
1

D'après ce que j'ai lu quelque part, si vous liez une nouvelle valeur à une variable dynamique dans Clojure, cette nouvelle valeur n'est disponible que dans ce thread.Dynamic var et Thread/sleep

Ainsi, afin de tester, je créé ce code:

(def *dynamic-var* "dynamic var") 

(defn run-it [] 
    (future (binding [*dynamic-var* "new-value"] (Thread/sleep 3000) (println *dynamic-var*))) 
    (future (Thread/sleep 1000) (println *dynamic-var*))) 

Ma question est: pourquoi le premier fil (qui doit imprimer « nouvelle valeur ») ne jamais courir? Il n'imprime jamais de "nouvelle valeur" sur la console.

Répondre

1

Le problème est que vous devez marquer votre var aussi dynamique avec des métadonnées:

(def ^:dynamic *dynamic-var* "dynamic var") 

(defn run-it [] 
    (future (binding [*dynamic-var* "new-value"] (Thread/sleep 3000) (println *dynamic-var*))) 
    (future (Thread/sleep 1000) (println *dynamic-var*))) 

Avec ^:dynamic ajouté, lorsque vous exécutez (run-it) il imprimera:

dynamic var 
new-value 

Sans elle, vous probablement vu un avertissement imprimé:

Avertissement: dynamic-var non déclaré dynamique et n'est donc pas dynamiquement réindexable, mais son nom suggère le contraire. Veuillez indiquer ^: dynamique dynamique-var ou changez le nom.

+0

Merci, compris! Je fais la transition de Java typé statique à Clojure typé dynamique. Je suis habitué au support d'IDE et à faire tant d'erreurs comme celle-ci car l'outil ne me prévient pas. L '"avertissement" que vous avez mentionné ne s'est pas manifesté de toute façon. Merci! –

+0

De rien! J'ai eu l'avertissement quand je courais le code dans REPL, je n'ai pas vérifié s'il est imprimé quand il est exécuté en dehors de REPL. –