SlideShare a Scribd company logo
1 of 38
Download to read offline
入門core.async
core.async勉強会
2015/4/19@HaLake
@athos0220
アジェンダ
core.asyncとは
コアコンセプト
基本的なAPIの使い方
ちょっと進んだトピック
core.asyncとは?
core.asyncとは?
非同期プログラミング用ライブラリ
CSPライクなチャネル通信をベースとしている
Go言語のgoroutineにインスパイアされたgoブ
ロックを提供
コアコンセプト
チャネル
並行に動くタスク間で値を受け渡す通信路
producer channel consumer
チャネル
並行に動くタスク間で値を受け渡す通信路
producer channel consumer
チャネル
並行に動くタスク間で値を受け渡す通信路
producer channel consumer
チャネル
並行に動くタスク間で値を受け渡す通信路
producer consumer
実際にはバッファを持ったキュー
チャネル
並行に動くタスク間で値を受け渡す通信路
producer consumer
実際にはバッファを持ったキュー
チャネル
並行に動くタスク間で値を受け渡す通信路
producer consumer
実際にはバッファを持ったキュー
チャネル
並行に動くタスク間で値を受け渡す通信路
producer consumer
実際にはバッファを持ったキュー
チャネル
並行に動くタスク間で値を受け渡す通信路
producer consumer
実際にはバッファを持ったキュー
バッファがいっぱいだったら?
チャネル
並行に動くタスク間で値を受け渡す通信路
producer consumer
実際にはバッファを持ったキュー
バッファがいっぱいだったら? バッファが空だったら?
協調スレッド(IOCスレッド)
以下のような場合に制御が別のスレッドに切り替わる
値を受信しようとしたときにバッファが空
値を送信しようとしたときにバッファがいっぱい
IOC = Inversion of Control
(go
(while true
(let [v (<! ch)]
(println v))))
(go
(loop [i 0]
(>! ch i)
(recur (inc i))))
協調スレッド(IOCスレッド)
以下のような場合に制御が別のスレッドに切り替わる
値を受信しようとしたときにバッファが空
値を送信しようとしたときにバッファがいっぱい
IOC = Inversion of Control
(go
(while true
(let [v (<! ch)]
(println v))))
(go
(loop [i 0]
(>! ch i)
(recur (inc i))))
上記の場合には  が実行されずに制御が切り替わる(パーク)
協調スレッド(IOCスレッド)
グリーンスレッド(ネイティブスレッドでない)ので生成の
コストが低い
シングルスレッドの場合でも使える(ClojureScriptでも!)
native thread native thread native thread
IOCthread
IOCthread
IOCthread
IOCthread
IOCthread
IOCthread
IOCthread
IOCthread
IOCthread
基本的なAPIの使い方
チャネル生成と送受信
チャネル生成:chan
送信:>!, >!!
受信:<!, <!!
(let [ch (chan 2)]
(>!! ch 0)
(>!! ch 1)
[(<!! ch) (<!! ch)])
;=> [0 1]
チャネル生成と送受信
チャネル生成:chan
送信:>!, >!!
受信:<!, <!!
(let [ch (chan 2)]
(>!! ch 0)
(>!! ch 1)
[(<!! ch) (<!! ch)])
;=> [0 1]
バッファのサイズを指定
チャネル生成と送受信
ブロッキング ノンブロッキング
送信 >!!
バッファが一杯ならブロック
>!
バッファが一杯ならパーク
受信 <!!
バッファが空ならブロック
<!
バッファが空ならパーク
チャネル生成と送受信
ブロッキング ノンブロッキング
送信 >!!
バッファが一杯ならブロック
>!
バッファが一杯ならパーク
受信 <!!
バッファが空ならブロック
<!
バッファが空ならパーク
後述のgoマクロ内でのみ使用可
goマクロ
協調スレッドで処理を実行する
(let [ch (chan 2)]
(go (while true
(let [v (<! ch)]
(println “received” v))))
(>!! ch “hi”)
(>!! ch “there”))
;; received hi
;; received there
timeout
(let [t (timeout 100)
begin (System/currentTimeMillis)]
(<!! t)
(println “Waited”
(- (System/currentTimeMillis)
begin)))
;; Waited 100
タイムアウト用のチャネルを生成する
alts!
一度に複数のチャネルから待ち受ける
(let [c1 (chan)
c2 (chan)]
(go (while true
(let [[v ch] (alts! [c1 c2])]
(println “received" v))))
(go (>! c1 "hi"))
(go (>! c2 "there")))
;; received hi
;; received there
alts!
一度に複数のチャネルから待ち受ける
(let [c1 (chan)
c2 (chan)]
(go (while true
(let [[v ch] (alts! [c1 c2])]
(println “received" v))))
(go (>! c1 "hi"))
(go (>! c2 "there")))
;; received hi
;; received there
待ち受けるチャネル
alts!
一度に複数のチャネルから待ち受ける
(let [c1 (chan)
c2 (chan)]
(go (while true
(let [[v ch] (alts! [c1 c2])]
(println “received" v))))
(go (>! c1 "hi"))
(go (>! c2 "there")))
;; received hi
;; received there
待ち受けるチャネル
受信した値と受信元のチャネルが返る
alts! + timeout
受信を待ち受ける時間にタイムアウトを設定
(go
(let [c (chan)
begin (System/currentTimeMillis)]
(alts! [c (timeout 100)])
(println "Gave up after”
(- (System/currentTimeMillis)
begin)))
バッファいろいろ
buffer
一杯になったらパーク or ブロック
dropping-buffer
一杯になったら追加しようとした値をドロップ
sliding-buffer
一杯になったら最初に追加した値をドロップ
ちょっと進んだトピック
ちょっと進んだトピック
チャネル間の連携
高レベルAPI
deprecated API vs transducers
チャネル間の連携
pipe
mult/tap
pub/sub mix/admix
値を振り分ける“トピック”を
あらかじめ指定しておく
高レベルAPI
チャネルによる値の送受信をClojure標準のシー
ケンス処理にみなしたAPI
内部でgoマクロを利用してチャネル間での値の
受け渡しを勝手にやってくれる
高レベルAPIを組み合わせることでgoマクロを
使った低レベルな記述をする機会を減らせる
高レベルAPI
その他、into, merge, reduce, take 等が用意
されている
(defn split [p ch]
(let [tc (chan), fc (chan)]
(go (loop []
(let [v (<! ch)]
(if (nil? v)
(do (close! tc) (close! fc))
(when (>! (if (p v) tc fc) v)
(recur))))))
[tc fc]))
c.c.a/splitの定義(一部簡略化)
deprecated API vs transducers
高レベルAPIで提供されるような、チャネルか
ら得られる値を加工したいケースは多い
channel ??? channel
deprecated API vs transducers
core.asyncではチャネル用のmapやfilterも提
供していた
(let [ch (to-chan (range))]
[(<!! ch) (<!! ch) (<!! ch)])
;=> [0 1 2]
(let [ch (->> (to-chan (range))
(map< inc)
(map< #(* % %)))]
[(<!! ch) (<!! ch) (<!! ch)])
;=> [1 4 9]
deprecated API vs transducers
Clojure 1.7以降ではtransducerを使って同様の処理が書ける
チャネル生成時にtransducerを指定するとチャネルから取得
できる値はtransducerを適用した結果の値になる
(let [xform (comp (map inc)
(map #(* % %)))
ch (pipe (to-chan (range))
(chan 1 xform))]
[(<!! ch) (<!! ch) (<!! ch)])
;=> [1 4 9]
transducer
まとめ
core.asyncはチャネルベースの非同期プログラ
ミング用ライブラリ
goマクロを使うことで協調スレッドが利用でき
ClojureScriptでも並行に動くタスクを記述可能

More Related Content

What's hot

What's hot (20)

例外設計における大罪
例外設計における大罪例外設計における大罪
例外設計における大罪
 
WebAssemblyのWeb以外のことぜんぶ話す
WebAssemblyのWeb以外のことぜんぶ話すWebAssemblyのWeb以外のことぜんぶ話す
WebAssemblyのWeb以外のことぜんぶ話す
 
ふつうのcore.async
ふつうのcore.asyncふつうのcore.async
ふつうのcore.async
 
BuildKitによる高速でセキュアなイメージビルド
BuildKitによる高速でセキュアなイメージビルドBuildKitによる高速でセキュアなイメージビルド
BuildKitによる高速でセキュアなイメージビルド
 
Java仮想マシンの実装技術
Java仮想マシンの実装技術Java仮想マシンの実装技術
Java仮想マシンの実装技術
 
Fess/Elasticsearchを使った業務で使える?全文検索への道
Fess/Elasticsearchを使った業務で使える?全文検索への道Fess/Elasticsearchを使った業務で使える?全文検索への道
Fess/Elasticsearchを使った業務で使える?全文検索への道
 
Planet-scale Data Ingestion Pipeline: Bigdam
Planet-scale Data Ingestion Pipeline: BigdamPlanet-scale Data Ingestion Pipeline: Bigdam
Planet-scale Data Ingestion Pipeline: Bigdam
 
【関東GPGPU勉強会#4】GTX 1080でComputer Vision アルゴリズムを色々動かしてみる
【関東GPGPU勉強会#4】GTX 1080でComputer Visionアルゴリズムを色々動かしてみる【関東GPGPU勉強会#4】GTX 1080でComputer Visionアルゴリズムを色々動かしてみる
【関東GPGPU勉強会#4】GTX 1080でComputer Vision アルゴリズムを色々動かしてみる
 
Dockerの期待と現実~Docker都市伝説はなぜ生まれるのか~
Dockerの期待と現実~Docker都市伝説はなぜ生まれるのか~Dockerの期待と現実~Docker都市伝説はなぜ生まれるのか~
Dockerの期待と現実~Docker都市伝説はなぜ生まれるのか~
 
SolrとElasticsearchを比べてみよう
SolrとElasticsearchを比べてみようSolrとElasticsearchを比べてみよう
SolrとElasticsearchを比べてみよう
 
ぼくがAthenaで死ぬまで
ぼくがAthenaで死ぬまでぼくがAthenaで死ぬまで
ぼくがAthenaで死ぬまで
 
プログラムを高速化する話
プログラムを高速化する話プログラムを高速化する話
プログラムを高速化する話
 
テスト文字列に「うんこ」と入れるな
テスト文字列に「うんこ」と入れるなテスト文字列に「うんこ」と入れるな
テスト文字列に「うんこ」と入れるな
 
分散学習のあれこれ~データパラレルからモデルパラレルまで~
分散学習のあれこれ~データパラレルからモデルパラレルまで~分散学習のあれこれ~データパラレルからモデルパラレルまで~
分散学習のあれこれ~データパラレルからモデルパラレルまで~
 
backlogsでもCI/CDする夢を見る
backlogsでもCI/CDする夢を見るbacklogsでもCI/CDする夢を見る
backlogsでもCI/CDする夢を見る
 
CEDEC 2018 最速のC#の書き方 - C#大統一理論へ向けて性能的課題を払拭する
CEDEC 2018 最速のC#の書き方 - C#大統一理論へ向けて性能的課題を払拭するCEDEC 2018 最速のC#の書き方 - C#大統一理論へ向けて性能的課題を払拭する
CEDEC 2018 最速のC#の書き方 - C#大統一理論へ向けて性能的課題を払拭する
 
深層学習フレームワークにおけるIntel CPU/富岳向け最適化法
深層学習フレームワークにおけるIntel CPU/富岳向け最適化法深層学習フレームワークにおけるIntel CPU/富岳向け最適化法
深層学習フレームワークにおけるIntel CPU/富岳向け最適化法
 
ARM LinuxのMMUはわかりにくい
ARM LinuxのMMUはわかりにくいARM LinuxのMMUはわかりにくい
ARM LinuxのMMUはわかりにくい
 
IoT時代におけるストリームデータ処理と急成長の Apache Flink
IoT時代におけるストリームデータ処理と急成長の Apache FlinkIoT時代におけるストリームデータ処理と急成長の Apache Flink
IoT時代におけるストリームデータ処理と急成長の Apache Flink
 
SAT/SMTソルバの仕組み
SAT/SMTソルバの仕組みSAT/SMTソルバの仕組み
SAT/SMTソルバの仕組み
 

Viewers also liked

Viewers also liked (20)

言語設計者が意味論を書くときに考えていたこと
言語設計者が意味論を書くときに考えていたこと言語設計者が意味論を書くときに考えていたこと
言語設計者が意味論を書くときに考えていたこと
 
KotlinJSって正直どうなん
KotlinJSって正直どうなんKotlinJSって正直どうなん
KotlinJSって正直どうなん
 
Polyglot on the JVM with Graal (Japanese)
Polyglot on the JVM with Graal (Japanese)Polyglot on the JVM with Graal (Japanese)
Polyglot on the JVM with Graal (Japanese)
 
Jvm言語とJava、切っても切れないその関係
Jvm言語とJava、切っても切れないその関係Jvm言語とJava、切っても切れないその関係
Jvm言語とJava、切っても切れないその関係
 
クラウド、クラウドというけれどJavaのシステムにとってクラウドってメリットあるの?
クラウド、クラウドというけれどJavaのシステムにとってクラウドってメリットあるの?クラウド、クラウドというけれどJavaのシステムにとってクラウドってメリットあるの?
クラウド、クラウドというけれどJavaのシステムにとってクラウドってメリットあるの?
 
Graph Algorithms Part 1
Graph Algorithms Part 1Graph Algorithms Part 1
Graph Algorithms Part 1
 
Open Liberty: オープンソースになったWebSphere Liberty
Open Liberty: オープンソースになったWebSphere LibertyOpen Liberty: オープンソースになったWebSphere Liberty
Open Liberty: オープンソースになったWebSphere Liberty
 
2017spring jjug ccc_f2
2017spring jjug ccc_f22017spring jjug ccc_f2
2017spring jjug ccc_f2
 
Jjugccc2017spring-postgres-ccc_m1
Jjugccc2017spring-postgres-ccc_m1Jjugccc2017spring-postgres-ccc_m1
Jjugccc2017spring-postgres-ccc_m1
 
Arachne Unweaved (JP)
Arachne Unweaved (JP)Arachne Unweaved (JP)
Arachne Unweaved (JP)
 
VMの歩む道。 Dalvik、ART、そしてJava VM
VMの歩む道。 Dalvik、ART、そしてJava VMVMの歩む道。 Dalvik、ART、そしてJava VM
VMの歩む道。 Dalvik、ART、そしてJava VM
 
U-NEXT学生インターン、過激なJavaの学び方と過激な要求
U-NEXT学生インターン、過激なJavaの学び方と過激な要求U-NEXT学生インターン、過激なJavaの学び方と過激な要求
U-NEXT学生インターン、過激なJavaの学び方と過激な要求
 
Java libraries you can't afford to miss
Java libraries you can't afford to missJava libraries you can't afford to miss
Java libraries you can't afford to miss
 
Java8移行は怖くない~エンタープライズ案件でのJava8移行事例~
Java8移行は怖くない~エンタープライズ案件でのJava8移行事例~Java8移行は怖くない~エンタープライズ案件でのJava8移行事例~
Java8移行は怖くない~エンタープライズ案件でのJava8移行事例~
 
Jjug ccc
Jjug cccJjug ccc
Jjug ccc
 
Kotlin is charming; The reasons Java engineers should start Kotlin.
Kotlin is charming; The reasons Java engineers should start Kotlin.Kotlin is charming; The reasons Java engineers should start Kotlin.
Kotlin is charming; The reasons Java engineers should start Kotlin.
 
SpotBugs(FindBugs)による 大規模ERPのコード品質改善
SpotBugs(FindBugs)による 大規模ERPのコード品質改善SpotBugs(FindBugs)による 大規模ERPのコード品質改善
SpotBugs(FindBugs)による 大規模ERPのコード品質改善
 
Polyglot on the JVM with Graal (English)
Polyglot on the JVM with Graal (English)Polyglot on the JVM with Graal (English)
Polyglot on the JVM with Graal (English)
 
Introduction of Project Jigsaw
Introduction of Project JigsawIntroduction of Project Jigsaw
Introduction of Project Jigsaw
 
Java Clientで入門する Apache Kafka #jjug_ccc #ccc_e2
Java Clientで入門する Apache Kafka #jjug_ccc #ccc_e2Java Clientで入門する Apache Kafka #jjug_ccc #ccc_e2
Java Clientで入門する Apache Kafka #jjug_ccc #ccc_e2
 

More from sohta

More from sohta (10)

Clojureシンタックスハイライター開発から考えるこれからのlispに必要なもの
Clojureシンタックスハイライター開発から考えるこれからのlispに必要なものClojureシンタックスハイライター開発から考えるこれからのlispに必要なもの
Clojureシンタックスハイライター開発から考えるこれからのlispに必要なもの
 
入門Transducers
入門Transducers入門Transducers
入門Transducers
 
Clojure Language Update (2015)
Clojure Language Update (2015)Clojure Language Update (2015)
Clojure Language Update (2015)
 
入門ClojureScript
入門ClojureScript入門ClojureScript
入門ClojureScript
 
プログラミング言語Clojureのニャンパスでの活用事例
プログラミング言語Clojureのニャンパスでの活用事例プログラミング言語Clojureのニャンパスでの活用事例
プログラミング言語Clojureのニャンパスでの活用事例
 
REPLライフをもっと快適に
REPLライフをもっと快適にREPLライフをもっと快適に
REPLライフをもっと快適に
 
genuine-highlighter: マクロを認識するClojure向けのシンタックスハイライター
genuine-highlighter: マクロを認識するClojure向けのシンタックスハイライターgenuine-highlighter: マクロを認識するClojure向けのシンタックスハイライター
genuine-highlighter: マクロを認識するClojure向けのシンタックスハイライター
 
ClojureではじめるSTM入門
ClojureではじめるSTM入門ClojureではじめるSTM入門
ClojureではじめるSTM入門
 
Macros in Clojure
Macros in ClojureMacros in Clojure
Macros in Clojure
 
Clojureによるバイトコードプログラミング
ClojureによるバイトコードプログラミングClojureによるバイトコードプログラミング
Clojureによるバイトコードプログラミング
 

入門core.async