問題タブ [core.async]
For questions regarding programming in ECMAScript (JavaScript/JS) and its various dialects/implementations (excluding ActionScript). Note JavaScript is NOT the same as Java! Please include all relevant tags on your question; e.g., [node.js], [jquery], [json], [reactjs], [angular], [ember.js], [vue.js], [typescript], [svelte], etc.
clojure - core.async は Clojure の原則に反していませんか?
多くの Clojure プログラマーが新しい core.async ライブラリに熱狂しているのを見てきました。非常に興味深いように思えますが、Clojure の原則にどのように準拠しているかを理解するのに苦労しているため、次の質問があります。
- 関数名が示すように、alt!、put!、>! などのように感嘆符が付けられているため、どこでも変更可能な状態を使用します。チャネルから値を入力または取得すると、そのチャネルはその場で変更されます。不変のデータ構造や純粋な関数などを好むという Clojure の哲学に反していませんか? それとも、変更可能なものをまったく回避できない場合にのみ、core.async を使用するように作られていますか?
「go」はマクロ(したがってコード構造を変更する)であり、「<!」を保証するためです。go-block で直接使用する場合、"<!" を使用することはできません。次のように、別の関数内で:
これが単純さと構成可能性を妨げているように私には思えます。問題にならないのはなぜですか?
おそらく、前の 2 つの問題の結果として、core.async を使用する多くのコードで、map/filter/reduce の代わりに loop/recur などの下位レベルの構造が使用されています。一歩後退じゃない?
ポイントがどこにありませんか?
前もって感謝します。
multithreading - Clojure core.async、タイムアウト後に CPU がハングします。とにかく、(go..) ブロックによって生成されたマクロ スレッドを適切に強制終了するには?
core.async walk through exampleに基づいて、以下の同様のコードを作成し、10 秒のタイムアウトで複数のチャネルを使用して CPU を集中的に使用するジョブを処理しました。ただし、メインスレッドが戻った後、CPU 使用率は約 700% のままです (8 CPU マシン)。Java プロセスをシャットダウンするには、emacs で手動で nrepl-close を実行する必要があります。
(go..) block によって生成されたマクロスレッドを強制終了する適切な方法はありますか? 近づいてみた!それぞれのちゃんですが、うまくいきません。メインスレッドが戻った後、JavaプロセスによってCPU使用率が0に戻ることを確認したい。
multithreading - Clojure core.async、その(行く...)スレッドプールのスレッド数を制御する方法はありますか?
デフォルトでは (go..) は、コア数の 2 倍 + 42 スレッドをスレッド プールに使用します。環境変数または sth を設定することで、コードが使用できるスレッドの数または CPU の数を設定する方法はありますか?
Linux マシンでは、taskset
を使用して CPU の数を設定できます。 taskset -c 0,1 my_Java_or_Clojure_program
(-> (java.lang.Runtime/getRuntime) .availableProcessors)
asynchronous - Clojure の core.async は Jane Street の OCaml Core Async に似ていますか?
このブログ投稿で、著者は次のように書いています。
ただし、Grenchman は、OCaml の最大の産業ユーザーの 1 つである Jane Street の Core および Async ライブラリに基づいて構築されています。Async は、他のイベント ドリブン ツールの多くのコールバックの頭痛の種を回避するモナドの擬似同時実行を可能にしますが、かなりモノリシックです。
Core Async の Jane Street Documentation Pageでは、次のように説明されています。
特に、Async はプログラムの同時実行性をより適切に制御し、競合状態の可能性について簡単に判断できると考えています。
私の質問は、Clojure の core.asyncと OCaml の Core Async の間に類似点はありますか? 「コールバックの問題を回避するための偽の並行性」は、Clojure での core.async の適用と非常によく似ているためです。
clojure - go マクロの制限を回避するための可能な解決策: (go ...) ブロック内で呼び出す必要があります
おそらく、(<! c)
外部の go マクロを使用するための可能な解決策は、マクロとそのマクロ展開時間で実行できます。
これは私の例です:
そしてそれをテストするには:
私はネストされたgoでこのソリューションを試しましたが、うまくいきます。しかし、それが正しい道であるかどうかはわかりません
この質問の理由は、この他の質問に関連しています 、@aeuhuea は、「これが単純さと構成可能性を妨げているように思えます。なぜ問題にならないのでしょうか?」とコメントしています。および @cgrand 応答「go マクロ (その局所性) の制限も機能です。ステートフル操作のソース コードの局所性を強制します。」しかし、コードを強制的にローカライズすることは、「完全にする」ことと同じではありませんか?
clojure - clojure core.async の機能拡張
独自の非同期関数で core.async の機能を拡張することは推奨されますか?
チャネルの非同期性は、コールバックを受け入れるput!
およびによって処理されますが、プロトコルは名前空間take!
にネストされています。implは近づかないことを意味async.impl.protocols
しますか?この場合、またはそれらを実装しても大丈夫ですか?
たとえば、Netty チャネルまたは Java ソケットを ReadPort および WritePort としてラップできます。
java - キル時に Clojure core.async go ループを正常に終了する
トップレベルのcore.async go ループがあります。少なくともCTRL-Cまたはkillなどで停止するように通知するまで、無期限に実行したい. 現在、次のようにjava.lang.Runtime/addShutdownHookを使用しています。
ここに私の問題があります:
REPL を開始する
(run)
と、バックグラウンド スレッドで開始および実行されます。REPL を終了すると、目的のシャットダウン メッセージが表示されません。ただし、から実行する
lein run
と、go ループがすぐに終了し、「SHUTDOWN」と表示されます。
どちらも私が欲しいものではありません。
すべての JVM で機能するソリューションが見つかるとは限りません。私は Mac で開発し、Ubuntu にデプロイするので、両方で機能するソリューションを見つけたいと思います。
Mac JVM: Java バージョン "1.7.0_45" Java(TM) SE ランタイム環境 (ビルド 1.7.0_45-b18) Java HotSpot(TM) 64 ビット サーバー VM (ビルド 24.45-b08、混合モード)
Ubuntu JVM: Java バージョン "1.7.0_25" OpenJDK ランタイム環境 (IcedTea 2.3.10) (7u25-2.3.10-1ubuntu0.12.04.2) OpenJDK 64 ビット サーバー VM (ビルド 23.7-b01、混合モード)
multithreading - Future vs Thread: core.async でチャネルを操作するのに適しているのはどれですか?
チャネルを操作する場合、 がfuture
推奨されthread
ますか? future
もっと理にかなっている時はありますか?
core.async に関する Rich Hickey のブログ投稿でthread
は、以下の使用を推奨していfuture
ます。
これらの操作は、eg future で作成されたスレッドで使用できますが、go に類似したマクロ thread もあります。これは、ファーストクラスのスレッドを起動し、同様にチャネルを返します。チャネル作業には future よりも優先する必要があります。
~ http://clojure.com/blog/2013/06/28/clojure-core-async-channels.html
ただし、core.async の例ではfuture
、チャネルを操作するときに を広範囲に使用しています。
~ https://github.com/clojure/core.async/blob/master/examples/ex-async.clj
asynchronous - core.async と Functional Reactive Programming (+Rx) の比較
Clojure のcore.asyncをいわゆるReactive Extensions (Rx) やFRP全般と比較すると、少し混乱しているようです。彼らは非同期性という同様の問題に取り組んでいるように見えるので、主な違いは何なのか、どのような場合にどちらが優先されるのか疑問に思います。誰か説明してくれませんか?
編集:より詳細な回答を促すために、質問をより具体的にしたいと思います:
Core.async を使用すると、同期のように見えるコードを記述できます。ただし、私が理解しているように、FRP は 1 レベルのネストされたコールバックしか必要としません (ロジックを処理するすべての関数は引数として FRP API に渡されます)。これは、両方のアプローチがコールバックピラミッドを不要にしているようです。
function() {...}
JS では何度も書かなければならないのは事実ですが、FRP ではネストされたコールバックという主な問題も解消されています。私はそれを正しく理解していますか?「FRPはメッセージの伝達を制御の流れで完結させます」 どなたか具体的に説明していただけますか?
チャネルを渡すのと同じ方法で、FRP の監視可能なエンドポイントを渡すことはできませんか?
一般に、両方のアプローチが歴史的にどこから来たのかを理解しており、両方のチュートリアルをほとんど試していません。しかし、私は違いの非自明性によって「麻痺」しているようです。これらのいずれかで書くのが難しく、他のコードを使用すると簡単なコードの例はありますか? そして、そのアーキテクチャ上の理由は何ですか?
clojure - Clojure の core.async を「継続渡しスタイル」と表現できますか?
Clojure のcore.async ライブラリには、ブロックをラップしてブロック IO を処理するチャネルを作成するステート マシンを作成するマクロがあります。go
これは、 C#とGo-lang の goroutinesでモデリングし ているようです。async
The Seasoned Schemerでは、継続を渡すためのテクニックについて説明しています。(これは call/cc に基づいているようです)。また、Clojureの区切られた継続に関するDavid Nolenのライブラリも見られます。
ここでは、C#async
を「現在の継続を伴う呼び出し」と表現しています。
私の質問は、Clojure の core.async を「継続渡しスタイル」と記述できるかということです。
または、「継続」(区切られたものと区切られていないもの) はオーバーロードされた用語ですか?
編集: 追加の注意事項 - David Nolen は、core.async に対して wrt を言っています:
go ブロックの内部では、継続渡しスタイルでコードを手動で記述する必要がないように、これらのことを同期的に実行できるという錯覚を与えます。