Your SlideShare is downloading. ×
歌舞伎座tech発表資料 RxJSの中を追う
Upcoming SlideShare
Loading in...5
×

Thanks for flagging this SlideShare!

Oops! An error has occurred.

×
Saving this for later? Get the SlideShare app to save on your phone or tablet. Read anywhere, anytime – even offline.
Text the download link to your phone
Standard text messaging rates apply

歌舞伎座tech発表資料 RxJSの中を追う

226
views

Published on

歌舞伎座techのRxJSの内部処理を追ったスライドです。Hot/Coldのお話とか。

歌舞伎座techのRxJSの内部処理を追ったスライドです。Hot/Coldのお話とか。

Published in: Software

0 Comments
2 Likes
Statistics
Notes
  • Be the first to comment

No Downloads
Views
Total Views
226
On Slideshare
0
From Embeds
0
Number of Embeds
0
Actions
Shares
0
Downloads
0
Comments
0
Likes
2
Embeds 0
No embeds

Report content
Flagged as inappropriate Flag as inappropriate
Flag as inappropriate

Select your reason for flagging this presentation as inappropriate.

Cancel
No notes for slide

Transcript

  • 1. RxJSの中を追う 安福 一樹 (wilfrem, @WilfremLuminous)
  • 2. 自己紹介 名前: 安福 一樹 HN: wilfremとか@WilfremLuminous 仕事 Webエンジニア。 主にサーバサイドの開発をしています。 最近新部署に異動しました。 趣味 最近は面白技術を色々試して遊んでいる
  • 3. はじめに
  • 4. 今日のタイトルについて RxのHot/Coldを入り口に Rxが中で何をやっているかを追いたいと思い ます。 主に細かなところについて。 Rxにはどうしてもハマる点あるのですが Rxが中で何をやっているかが分かれば ハマりどころを回避できると思います。
  • 5. 対象プラットフォームについて RxJS中心のお話になっていますが Rx.NET/RxJavaの実装と見比べてみたところ 言語ごとの実装に大きな違いはなく Rx.NET/RxJavaでも使える話になります スケジューラーしか大きな違いが無かった オペレータ名が微妙に違うのも LINQ引きずってる.NETだけの話だし
  • 6. 本編
  • 7. まずはこの問題のコードを御覧ください “side effect”は何回表示されるか? var rx = require("rx"); var s = new rx.Subject(); var stream = s.tap(function(){console.log("side effect");}); stream.subscribeOnNext(function(){}); stream.subscribeOnNext(function(){}); s.onNext("foo"); ちょっと読みにくいので図にします
  • 8. 図にしてみた side effectは何回表示されるでしょうか? subject tap(do) side effect message onNext nop nop
  • 9. 答え 2回 subject tap(do) side effect message onNext nop nop side effect
  • 10. なぜ二回なのか? よくある説明 「doはColdなObservableだ」 →とても表面的な説明と理解 説明が良くない 現象の正しい理解のために Rxの動作原理を追ってみる
  • 11. Rxのおさらい
  • 12. Rxの基本要素 Rxのストリームと3種のメッセージ onNext* (onCompleted|onError)? onNext onNext onNext onCompleted
  • 13. ObservableとObserver onNext(msg: T) onCompleted() onError(error: any) Observer<T>Observable<T> subscribe(o: Observer<T>) 1. subscribeする 2. つながる 3. messageがpushされる
  • 14. Observableとオペレータ map filter throttle Observable map オペレータ=Observableを返す関数 RxにはObservableのメンバに様々なオペレータがある Observable
  • 15. オペレータのチェーン map filter throttleObservable Rxのオペレータは繋げられる メッセージはオペレータに”加工”されて伝達する(onCompleted/onErrorも同様) map filter throttleObservable Observer message onNext onNext onNext onNext message subscribe
  • 16. ところで……
  • 17. オペレータはObservableである オペレータを重ねられる subscribeできる →Observableである Observable map オペレータはObservableである Observable
  • 18. オペレータはObserverでもある? Observableに繋げられる メッセージを受け取れる →Observerである Observable map オペレータはObserverでもある Observer message Observer?いた?
  • 19. しかし、オペレータの利用で Observerを見かけることはない
  • 20. Observerはどこにいるのか?
  • 21. 改めて: ObservableとObserver onNext(msg: T) onCompleted() onError(error: any) Observer<T>Observable<T> subscribe(o: Observer<T>) 1. subscribeする 2. つながる 3. messageがpushされる
  • 22. 当然ですが、オペレータ=Observable  何度も説明したとおり、オペレータ=Observable  つまり、後ろのObserverにsubscribeされる  もちろん、後ろがオペレーターなら オペレーターがオペレーターをsubscribeする  どうやって……? map filter throttleObservable Observer subscribe
  • 23. オペレーターがオペレーターを Subscribeする方法とは?
  • 24. 答え: オペレータはObserverを生成する Observerを「生成」する 1つ手前のObservableをsubscribeする subscribeはチェーンする map filter throttleObservable Observer subscribe throttleObserver
  • 25. Subscribeが完了すると 最終的にObservableにチェーンが到達 結果的にSubscribeすると Observerのチェーンが生成される map filter throttleObservable Observer メッセージ メッセージ メッセージ
  • 26. オペレータの内部実装 ObservableBase(的な物)がある  =AnnonimousObservable  パフォーマンス改善verだと まさにObservableBaseが存在する subscribeだけ差し替えられる 各オペレータはsubscribeの差し替えを実装 差し替え処理で手前をsubscribeしている
  • 27. Rxの”Hot”とは? Hot = Observerのチェーンを作ること。 Observerのチェーンを作るから メッセージが流れる RxのHotとは subscribeしてチェーンを作成すること。
  • 28. チェインの行き着く先について
  • 29. チェインの行き着く先 一番先頭のObservableはどういう物か? 2種類のObservableが存在する map filter throttleObservable Observer ?
  • 30. タイプ1: “非保持型” 特徴  subscribeしてきたObserverを保持しない  何回subscribeしても同じ結果となる →例えばチェーンを何度も生成 例  just, create、大抵のオペレータなど =”Cold Observable”、Coldな性質と呼ばれる
  • 31. タイプ2: “保持型” 特徴  subscribeしてきたobservableをキャプチャする  必要になった時にメッセージを流す  流す対象をリストとして持ち、分配機能を持つ 例  publish, fromEvent, Subject = “Hot Observable”、Hotな性質と呼ばれる Hot/Coldが分かりにくいのは 用語間違っているからな気がしている
  • 32. 話をだいぶ戻して side effectはなぜ2回表示されるか? subject tap(do) side effect message onNext nop nop もう分かりますよね。
  • 33. こうなるから subject tap(do) side effect message onNext nop nop side effect tap observer tap observer
  • 34. では? side effectを1回だけ表示させるには? subject tap(do) side effect message onNext nop nop
  • 35. 答え subjectを挟む subject tap(do) side effect message onNext nop nop subject
  • 36. Subjectの役割 役割  SubjectはObserverをリストとして持つ  Observerとしてメッセージを受け取る  Observableとしてメッセージを配信する Subjectを挟むと”保持型”になる =Cold→Hot変換の正体  publish, share, fromeventは 内部でSubject使っている
  • 37. Cold→Hot変換のconnect()とは Cold→Hot変換すると出てくる ConnectableObservable 中にSubjectがいる。 ConnectableObservable = Subject ConnectableObservable#connect()とは 内部のsubjectにsubscribeさせること。
  • 38. 改めて、Rxは中で何をやっているのか? 復習を兼ねて
  • 39. Rxの構成要素 Rxは (乱暴めに言うと) 5つの要素で構成されている Observable Observer ObserverとObservable BaseObservableと オペレータ subjectoperator SubjectとHot onNext* (onCompleted | onError)? scheduler Scheduler おまけで解説します ストリーム
  • 40. Observableとオペレーター Observableに Operatorを繋げて 次のObservableを得 られる Observable Observable operator Observable
  • 41. Observableとオペレーターの関係 オペレータは 手前の参照を持つ 後ろの参照はしな い メッセージは まだ流れない この状態=Cold Observable operator 参照 参照せず
  • 42. Operatorの仕組み オペレータはほぼ 処理が共通 =ObservableBase subscribeを差し替え られるのみ Operator extends ObservableBase<T> subscribe(o: Observer<T>) 差し替え可能 Rxのオペレータは多数存在するが 大半はここの差し替えの違いのみ
  • 43. subscribe差し替えの例 filter 条件に一致した時 に 次にメッセージを 流すObserverを 作成する map メッセージを変換 して流す Observerを作成する
  • 44. subscribeの連鎖 Subscribe連鎖 Subscribeで 後ろのObserverを知 る Observerのチェーン が作成される Observable operator subscribe Observer Observer 参照
  • 45. ストリームの作動 連鎖が完了 →Observerのチェー ンが完成 これで「作動」し メッセージが流れ る →Hotになる Observable operator Observer Observerメッセージ
  • 46. Cold “Observable”とHot “Observable” Cold “Observable” Observer非保持 オペレータなら subscribeごとに チェーンを生成 Hot “Observable” Observer保持 分配機能を持つ Subjectでできている
  • 47. メッセージの伝搬 Observer onNext() onCompleted() onError() Observer onNext() onCompleted() onError() message message message
  • 48. メッセージはSubscribeに到達する Observer onNext() onCompleted() onError() subscriber subscribeOnNext() subscribeOnCompleted() subscribeOnError() message message
  • 49. ストリームの終了 disposeを呼ぶか ストリームが終了で チェーンは消滅Observable operator Observer Observer Observable operator Observer dispose()
  • 50. 以上がRxの中身になります
  • 51. おまけ: Schedulerについて 流れ的に入らなかった……
  • 52. スケジューラーとは  実行する関数をイベントキューに積む機構  メッセージの送信タイミングを変えられる  スレッドも変えられる 関数 イベントキュー スレッド・イベントループ 関数 関数 キューに積む 実行
  • 53. Schedulerの実装 Rxの実装方法は言語によって違いはない 例外がScheduler スレッドが使えるかどうか? イベントループはあるか?
  • 54. Rx.NET/RxJavaのScheduler 出来ること  スレッド切り替え(新規スレッド・ワーカー)  スレッド同期  イベントキューへの積み込み  etc. 大体の物は用意されている
  • 55. RxJSにおけるScheduler イベントループに積む/積まないのみ。  シングルスレッドですし…… Scheduler.defaultが使える 積む関数は適切に選ばれる  node.jsはsetImmediate→nextTick  ブラウザはsetImmediate→MessageChannnel→ postMessage→onReadyStateChanged→ setTimeout
  • 56. スケジューラーの使いどころ 重たい処理 処理を一息つかせたい時 スレッド切り替え/同期したい時
  • 57. observeOnとsubscribeOnの違い observeOn メッセージが来た時 メッセージ処理に イベントループや スレッド切り替えを 挟む subscribeOn subscribe時の チェーン生成時 チェーン生成の スレッドを変えられ る 何に使うんだろ?
  • 58. 以上です ご清聴ありがとうございました