Upgrade to Pro — share decks privately, control downloads, hide ads and more …

RxSwiftは開発をどう変えたか?

 RxSwiftは開発をどう変えたか?

8889da6a67db3667b0694d993c9a962c?s=128

Yosuke Ishikawa

August 20, 2016
Tweet

Transcript

  1. RxSwi は開発を どう変えたか?

  2. None
  3. RxSwi

  4. RxSwi イベントストリー ムを抽象化

  5. - - - - - - - [ a ]

    - - - - - - - - - - - - - [ a b ] - - - - - - - - - - - - - [ a b c ] - - - - - - -
  6. Observable<Element> イベントストリー ムを表す型

  7. l e t t e x t F i e

    l d = U I T e x t F i e l d ( ) l e t t e x t = t e x t F i e l d . r x _ t e x t / / O b s e r v a b l e < S t r i n g >
  8. subscribe(_:) イベントごとにクロー ジャを実行

  9. l e t t e x t F i e

    l d = U I T e x t F i e l d ( ) l e t t e x t = t e x t F i e l d . r x _ t e x t t e x t . s u b s c r i b e { p r i n t ( $ 0 ) } イベントごとに値を出力
  10. None
  11. bindTo(_:) Observer<Element>( 概念) に自動反映する

  12. l e t t e x t F i e

    l d = U I T e x t F i e l d ( ) l e t l a b e l = U I L a b e l ( ) t e x t F i e l d . r x _ t e x t . b i n d T o ( l a b e l . r x _ t e x t ) UITextField からUILabel に自動反映
  13. None
  14. RxSwi はイベントストリー ムを抽象化するライブラリ イベントストリー ムはObservable<Element> で表される subscribe(_:) でイベントを個別に受け取れる bindTo(_:) でイベントストリー

    ムを接続できる
  15. Operator Observable の変換・ 絞り込み・ 組み合わせ

  16. 変換 : map, flatMap, scan, debounce 絞り込み : filter, take,

    skip, distinct 組み合わせ : zip, combineLatest, merge, sample, concat
  17. t e x t F i e l d .

    r x _ t e x t . m a p { " \ ( $ 0 . c h a r a c t e r s . c o u n t ) " } . b i n d T o ( l a b e l . r x _ t e x t ) UITextField の文字数をUILabel にバインド
  18. None
  19. None
  20. l e t b u t t o n =

    U I B u t t o n ( ) l e t t e x t F i e l d 1 = U I T e x t F i e l d ( ) l e t t e x t F i e l d 2 = U I T e x t F i e l d ( ) l e t l a b e l = U I L a b e l ( ) O b s e r v a b l e . c o m b i n e L a t e s t ( t e x t F i e l d 1 . r x _ t e x t , t e x t F i e l d 2 . r x _ t e x t ) { " \ ( $ 0 ) \ ( $ 1 ) " } . s a m p l e ( b u t t o n . r x _ t a p ) . b i n d T o ( l a b e l . r x _ t e x t ) . a d d D i s p o s a b l e T o ( d i s p o s e B a g )
  21. Rx vs 従来方式 イベントストリー ムの扱いの違い

  22. Rx

  23. c l a s s V i e w C

    o n t r o l l e r : U I V i e w C o n t r o l l e r { @ I B O u t l e t w e a k v a r t e x t F i e l d 1 : U I T e x t F i e l d ! @ I B O u t l e t w e a k v a r t e x t F i e l d 2 : U I T e x t F i e l d ! @ I B O u t l e t w e a k v a r b u t t o n : U I B u t t o n ! @ I B O u t l e t w e a k v a r l a b e l : U I L a b e l ! p r i v a t e l e t d i s p o s e B a g = D i s p o s e B a g ( ) f u n c v i e w D i d L o a d ( ) { s u p e r . v i e w D i d L o a d ( ) O b s e r v a b l e . c o m b i n e L a t e s t ( t e x t F i e l d 1 . r x _ t e x t , t e x t F i e l d 2 . r x _ t e x t ) { " \ ( $ 0 ) \ ( $ 1 ) " } . s a m p l e ( b u t t o n . r x _ t a p ) . b i n d T o ( l a b e l . r x _ t e x t ) . a d d D i s p o s a b l e T o ( d i s p o s e B a g ) } }
  24. 水道にホー スをつなぐイメー ジ

  25. Observable<String> × 2

  26. combineLatest(_:_:)

  27. sample(_:)

  28. c l a s s V i e w C

    o n t r o l l e r : U I V i e w C o n t r o l l e r { . . . f u n c v i e w D i d L o a d ( ) { s u p e r . v i e w D i d L o a d ( ) O b s e r v a b l e . c o m b i n e L a t e s t ( t e x t F i e l d 1 . r x _ t e x t , t e x t F i e l d 2 . r x _ t e x t ) { " \ ( $ 0 ) \ ( $ 1 ) " } . s a m p l e ( b u t t o n . r x _ t a p ) . b i n d T o ( l a b e l . r x _ t e x t ) . a d d D i s p o s a b l e T o ( d i s p o s e B a g ) } }
  29. c l a s s V i e w C

    o n t r o l l e r : U I V i e w C o n t r o l l e r { @ I B O u t l e t w e a k v a r t e x t F i e l d 1 : U I T e x t F i e l d ! @ I B O u t l e t w e a k v a r t e x t F i e l d 2 : U I T e x t F i e l d ! @ I B O u t l e t w e a k v a r b u t t o n : U I B u t t o n ! @ I B O u t l e t w e a k v a r l a b e l : U I L a b e l ! @ I B A c t i o n f u n c b u t t o n D i d T a p ( s e n d e r B u t t o n : U I B u t t o n ) l a b e l . t e x t = " \ ( t e x t F i e l d 1 . t e x t ) \ ( t e x t F i e l d 2 . t e x t ) " } }
  30. バケツに水を入れるイメー ジ

  31. UITextField × 2

  32. UILabel

  33. c l a s s V i e w C

    o n t r o l l e r : U I V i e w C o n t r o l l e r { @ I B O u t l e t w e a k v a r t e x t F i e l d 1 : U I T e x t F i e l d ! @ I B O u t l e t w e a k v a r t e x t F i e l d 2 : U I T e x t F i e l d ! @ I B O u t l e t w e a k v a r b u t t o n : U I B u t t o n ! @ I B O u t l e t w e a k v a r l a b e l : U I L a b e l ! @ I B A c t i o n f u n c b u t t o n D i d T a p ( s e n d e r B u t t o n : U I B u t t o n ) l a b e l . t e x t = " \ ( t e x t F i e l d 1 . t e x t ) \ ( t e x t F i e l d 2 . t e x t ) " } }
  34. Rx すべてのイベントストリー ムの表現手段が同じ 貯めておいて後で取りに行くという動作がない イベントストリー ムの依存関係がoperator で表され る

  35. 現在地の天気アプリ

  36. None
  37. 1. ボタンのタップ 2. 位置情報の利用の認可状態 3. 位置情報 4. 天気API のレスポンス

  38. e n u m W e a t h e

    r { c a s e S u n n y , C l o u d y , R a i n y v a r d e s c r i p t i o n : S t r i n g { s w i t c h s e l f { c a s e . S u n n y : r e t u r n " 晴 " c a s e . C l o u d y : r e t u r n " 曇 " c a s e . R a i n y : r e t u r n " 雨" } } } 天気
  39. f i n a l c l a s s

    W e a t h e r A P I { s t a t i c f u n c g e t ( l o c a t i o n l o c a t i o n : C L L o c a t i o n , h a n d l e r : l e t d e l a y = 1 . 0 * D o u b l e ( N S E C _ P E R _ S E C ) l e t t i m e = d i s p a t c h _ t i m e ( D I S P A T C H _ T I M E _ N O W , I n t 6 4 d i s p a t c h _ a f t e r ( t i m e , d i s p a t c h _ g e t _ m a i n _ q u e u e ( ) ) { h a n d l e r ( W e a t h e r . r a n d o m ) } } } 天気API
  40. e n u m L o c a t i

    o n S t a t u s { c a s e A u t h o r i z e d ( C L L o c a t i o n ) c a s e D e n i e d v a r d e s c r i p t i o n : S t r i n g { s w i t c h s e l f { c a s e . A u t h o r i z e d ( l e t l o c a t i o n ) : l e t l a t i t u d e = l o c a t i o n . c o o r d i n a t e . l a t i t u d e l e t l o n g i t u d e = l o c a t i o n . c o o r d i n a t e . l o n g i t u d e r e t u r n " \ ( l a t i t u d e ) , \ ( l o n g i t u d e ) " c a s e . D e n i e d : r e t u r n " 位置情報 利用 許可 " } } } 位置情報 + 認可情報
  41. 従来のUIViewController

  42. c l a s s G e o W e

    a t h e r V i e w C o n t r o l l e r : U I V i e w C o n t r o l l e r , C L L o c a t i o n @ I B O u t l e t w e a k v a r l o c a t i o n L a b e l : U I L a b e l ! @ I B O u t l e t w e a k v a r w e a t h e r L a b e l : U I L a b e l ! @ I B O u t l e t w e a k v a r b u t t o n : U I B u t t o n ! v a r l o c a t i o n S t a t u s : L o c a t i o n S t a t u s ? { d i d S e t { l o c a t i o n L a b e l . t e x t = l o c a t i o n S t a t u s ? . d e s c r i p t i o n ? ? " - " } } v a r w e a t h e r : W e a t h e r ? { d i d S e t { w e a t h e r L a b e l . t e x t = w e a t h e r ? . d e s c r i p t i o n ? ? " - " } } }
  43. @ I B A c t i o n f

    u n c b u t t o n D i d T a p ( s e n d e r B u t t o n : U I B u t t o n ) { s t a r t U p d a t i n g L o c a t i o n ( ) } f u n c s t a r t U p d a t i n g L o c a t i o n ( ) { l o c a t i o n M a n a g e r . d e l e g a t e = s e l f s w i t c h C L L o c a t i o n M a n a g e r . a u t h o r i z a t i o n S t a t u s ( ) { c a s e . N o t D e t e r m i n e d : l o c a t i o n M a n a g e r . r e q u e s t W h e n I n U s e A u t h o r i z a t i o n ( ) c a s e . A u t h o r i z e d A l w a y s , . A u t h o r i z e d W h e n I n U s e : l o c a t i o n M a n a g e r . s t a r t U p d a t i n g L o c a t i o n ( ) c a s e . D e n i e d , . R e s t r i c t e d : l o c a t i o n S t a t u s = . D e n i e d w e a t h e r = n i l } }
  44. / / M A R K : C L L

    o c a t i o n M a n a g e r D e l e g a t e f u n c l o c a t i o n M a n a g e r ( m a n a g e r : C L L o c a t i o n M a n a g e r , d i d C h a n g e A u s t a r t U p d a t i n g L o c a t i o n ( ) } f u n c l o c a t i o n M a n a g e r ( m a n a g e r : C L L o c a t i o n M a n a g e r , d i d U p d a t e L o g u a r d l e t l o c a t i o n = l o c a t i o n s . f i r s t e l s e { r e t u r n } l o c a t i o n M a n a g e r . s t o p U p d a t i n g L o c a t i o n ( ) l o c a t i o n M a n a g e r . d e l e g a t e = n i l W e a t h e r A P I . g e t ( l o c a t i o n : l o c a t i o n ) { [ w e a k s e l f ] w e a t h e r i n s e l f ? . l o c a t i o n S t a t u s = . A u t h o r i z e d ( l o c a t i o n ) s e l f ? . w e a t h e r = w e a t h e r } }
  45. コー ドの実行を追ってみると...

  46. None
  47. None
  48. None
  49. None
  50. None
  51. None
  52. None
  53. None
  54. パッと全体のフロー を把握するのは難しい

  55. Rx のUIViewController

  56. Live!

  57. 複雑な制御もバインドだけで実装できた 制御の依存関係が見えるようになった

  58. まとめ RxSwi は開発をどう変えたか?

  59. イベントストリー ムを宣言的に扱えるようになった 複雑なイベントストリー ムでも全体を把握しやすい ストアドプロパティによる状態管理を減らせる

  60. RxSwi どうですか?

  61. 宣伝 Swi の本を出します

  62. 言語の基礎仕様 + 言語仕様を活かした書き方 Swi 3.0 対応 冬に出る予定です!