2016-08-15 10 views
1

Clojureのあるスレッドから別のスレッドにコードを挿入する方法は?Clojureのあるスレッドから別のスレッドへコードを挿入する方法(REPLでのライブOpenGL編集用)?

私はLWJGLでClojureを使用しており、ゲームループを実装しています。 REPLを使ってインタラクティブに編集したい。その結果、私はループとすべてのOpenGL呼び出しをJava Runnablesを使用して別のスレッドに移動しました。私は外側からループを変更することでいくつかの成功を収めています:A.両方のスレッドにアクセス可能な原子を使用し、REPLスレッドからそれらを変更します。 (:color @globals)とB. Clojureコードをアトム(:code @globals)として格納し、REPLからそれを変更し、スレッドループ内で次のようにアクセスします:(eval (:code @globals))

しかし、Clojureのシンボルはすべて1つのスレッドにバインドされています。私は2と2つを追加するメッセージを送信することができます(+ 2 2)、しかしそれ以上のことを得ることはありません。

LISPとして、Clojureはデータの利点としてコードを持っています。 REPLスレッドを使ってグラフィックス・スレッドを変更したいが、シンボル・バインディングの問題を回避する必要がある。

マイループ:

(while (not (GLFW/glfwWindowShouldClose window)) 
    (eval (:code @globals)) 
    (GL11/glClearColor (get (:color @globals) 0) (get (:color @globals) 1) 
      (get (:color @globals) 2) (get (:color @globals) 3)) 
    ...... 
) 
+0

私はLWJGLでClojureでゲームを開発しようとしています。私の計画は、[Component](https://github.com/)と組み合わされたStuart Sierraの[再読み込みされたワークフロー](http://thinkrelevance.com/blog/2013/06/04/clojure-workflow-reloaded)を使用することですstuartsierra /コンポーネント)、[Suspendable](https://github.com/weavejester/suspendable)、[reloaded.repl'](https://github.com/weavejester/reloaded.repl)の各ライブラリにあります。これは私のためにかなりうまくいきました(http://codereview.stackexchange.com/q/126376/82369)(私はそれ以来、私が言及した問題の解決策を見つけました)。そのワークフローを調べることができます。 –

答えて

0

あなたが共有原子への値として、あなたの関数を渡すことができます。生のClojureコードをデータとして渡して評価する必要はありません。関数値を渡すだけでいいです:

(def my-function (atom (fn []))) 

(.start 
    (Thread. 
    (fn [] 
     (while true 
     (@my-function) 
     (Thread/sleep 1000))))) 

(reset! my-function 
    (fn [] (println "A"))) 

;; wait a few seconds  
;; prints 'A's with one second interval 


(reset! my-function 
    (fn [] (println "B"))) 

;; prints 'B's with one second interval 
+0

例をありがとう - 私は実際に関数を渡すとは思わなかった。私の懸念は、このやり方はまだ関数本体の中のどのvarsやアトムにもアクセスできないということです。ループの前には多くのLWJGLと頂点バッファなどのセットアップコードとvarsがあり、関数内でそれを参照できる必要があります。 Clojureのスレッドローカルバインディングを考えると、これをどうやって行うのか分かりません。 –

+0

各データをアトムに入れることができ、スレッド間で利用できるようになります。 –

関連する問題