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

Simplicity in composition

Simplicity in composition

Adelbert Chang

September 18, 2017
Tweet

More Decks by Adelbert Chang

Other Decks in Programming

Transcript

  1. Simplicity in composition
    Adelbert Chang
    @adelbertchang
    Scala World 2017
    Adelbert Chang (@adelbertchang) Simplicity in composition Scala World 2017 1 / 67

    View Slide

  2. Composition
    A: type (set) of values
    Adelbert Chang (@adelbertchang) Simplicity in composition Scala World 2017 2 / 67

    View Slide

  3. Composition
    A: type (set) of values
    ⊕: A × A → A
    Adelbert Chang (@adelbertchang) Simplicity in composition Scala World 2017 2 / 67

    View Slide

  4. Composition
    A: type (set) of values
    ⊕: A × A → A
    1A
    : identity for ⊕
    Adelbert Chang (@adelbertchang) Simplicity in composition Scala World 2017 2 / 67

    View Slide

  5. Composition
    A: type (set) of values
    ⊕: A × A → A
    1A
    : identity for ⊕
    (x ⊕ y) ⊕ z = x ⊕ (y ⊕ z)
    Adelbert Chang (@adelbertchang) Simplicity in composition Scala World 2017 2 / 67

    View Slide

  6. Composition
    A: type (set) of values
    ⊕: A × A → A
    1A
    : identity for ⊕
    (x ⊕ y) ⊕ z = x ⊕ (y ⊕ z)
    x = x ⊕ 1A
    = 1A
    ⊕ x
    Adelbert Chang (@adelbertchang) Simplicity in composition Scala World 2017 2 / 67

    View Slide

  7. (Z, +, 0)
    Adelbert Chang (@adelbertchang) Simplicity in composition Scala World 2017 3 / 67

    View Slide

  8. ([a], +
    +, [])
    Adelbert Chang (@adelbertchang) Simplicity in composition Scala World 2017 4 / 67

    View Slide

  9. (A → A, ◦, a → a)
    Adelbert Chang (@adelbertchang) Simplicity in composition Scala World 2017 5 / 67

    View Slide

  10. trait Monoid[A] {
    def combine(x: A, y: A): A
    def empty: A
    }
    Adelbert Chang (@adelbertchang) Simplicity in composition Scala World 2017 6 / 67

    View Slide

  11. 1 2 3 4 5 6 7 8
    Adelbert Chang (@adelbertchang) Simplicity in composition Scala World 2017 7 / 67

    View Slide

  12. 3 3 4 5 6 7 8
    Adelbert Chang (@adelbertchang) Simplicity in composition Scala World 2017 8 / 67

    View Slide

  13. 6 4 5 6 7 8
    Adelbert Chang (@adelbertchang) Simplicity in composition Scala World 2017 9 / 67

    View Slide

  14. 15 6 7 8
    Adelbert Chang (@adelbertchang) Simplicity in composition Scala World 2017 10 / 67

    View Slide

  15. 36
    Adelbert Chang (@adelbertchang) Simplicity in composition Scala World 2017 11 / 67

    View Slide

  16. 1 2 3 4 5 6 7 8
    Adelbert Chang (@adelbertchang) Simplicity in composition Scala World 2017 12 / 67

    View Slide

  17. 3 7 11 15
    Adelbert Chang (@adelbertchang) Simplicity in composition Scala World 2017 13 / 67

    View Slide

  18. 10 26
    Adelbert Chang (@adelbertchang) Simplicity in composition Scala World 2017 14 / 67

    View Slide

  19. 36
    Adelbert Chang (@adelbertchang) Simplicity in composition Scala World 2017 15 / 67

    View Slide

  20. 1 2 3 4 5 6 7 8
    3 7 11 15
    10 26
    36
    Adelbert Chang (@adelbertchang) Simplicity in composition Scala World 2017 16 / 67

    View Slide

  21. Associative composition allows for modular
    decomposition and reasoning.
    Adelbert Chang (@adelbertchang) Simplicity in composition Scala World 2017 17 / 67

    View Slide

  22. Composing programs
    A
    Adelbert Chang (@adelbertchang) Simplicity in composition Scala World 2017 18 / 67

    View Slide

  23. Composing programs
    F[A]
    Adelbert Chang (@adelbertchang) Simplicity in composition Scala World 2017 19 / 67

    View Slide

  24. Composing programs
    (F[A], F[A]) => F[A]
    Adelbert Chang (@adelbertchang) Simplicity in composition Scala World 2017 20 / 67

    View Slide

  25. Composing programs
    (F[A], F[B]) => F[?]
    Adelbert Chang (@adelbertchang) Simplicity in composition Scala World 2017 21 / 67

    View Slide

  26. Composing programs
    (F[A], F[B]) => F[(A, B)]
    Adelbert Chang (@adelbertchang) Simplicity in composition Scala World 2017 22 / 67

    View Slide

  27. Composing programs
    F( ): type of program
    Adelbert Chang (@adelbertchang) Simplicity in composition Scala World 2017 23 / 67

    View Slide

  28. Composing programs
    F( ): type of program
    ⊗ : F(A) × F(B) → F((A, B))
    Adelbert Chang (@adelbertchang) Simplicity in composition Scala World 2017 23 / 67

    View Slide

  29. Composing programs
    F( ): type of program
    ⊗ : F(A) × F(B) → F((A, B))
    η : A → F(A)
    Adelbert Chang (@adelbertchang) Simplicity in composition Scala World 2017 23 / 67

    View Slide

  30. Composing programs
    F( ): type of program
    ⊗ : F(A) × F(B) → F((A, B))
    η : A → F(A)
    (fa ⊗ fb) ⊗ fc ∼
    = fa ⊗ (fb ⊗ fc)
    Adelbert Chang (@adelbertchang) Simplicity in composition Scala World 2017 23 / 67

    View Slide

  31. Composing programs
    F( ): type of program
    ⊗ : F(A) × F(B) → F((A, B))
    η : A → F(A)
    (fa ⊗ fb) ⊗ fc ∼
    = fa ⊗ (fb ⊗ fc)
    fa ∼
    = fa ⊗ ηUnit

    = ηUnit
    ⊗ fa
    Adelbert Chang (@adelbertchang) Simplicity in composition Scala World 2017 23 / 67

    View Slide

  32. Composing programs
    def zipOption[A, B]
    (oa: Option[A], ob: Option[B]): Option[(A, B)] =
    (oa, ob) match {
    case (Some(a), Some(b)) => Some((a, b))
    case _ => None
    }
    Adelbert Chang (@adelbertchang) Simplicity in composition Scala World 2017 24 / 67

    View Slide

  33. Composing programs
    def zipOption[A, B]
    (oa: Option[A], ob: Option[B]): Option[(A, B)] =
    (oa, ob) match {
    case (Some(a), Some(b)) => Some((a, b))
    case _ => None
    }
    def pureOption[A](a: A): Option[A] = Some(a)
    Adelbert Chang (@adelbertchang) Simplicity in composition Scala World 2017 24 / 67

    View Slide

  34. Composing programs
    def zipList[A, B]
    (la: List[A], lb: List[B]): List[(A, B)] =
    la match {
    case Nil => Nil
    case h :: t => lb.map((h, _)) ++ zipList(t, lb)
    }
    Adelbert Chang (@adelbertchang) Simplicity in composition Scala World 2017 25 / 67

    View Slide

  35. Composing programs
    def zipList[A, B]
    (la: List[A], lb: List[B]): List[(A, B)] =
    la match {
    case Nil => Nil
    case h :: t => lb.map((h, _)) ++ zipList(t, lb)
    }
    def pureList[A](a: A): List[A] = List(a)
    Adelbert Chang (@adelbertchang) Simplicity in composition Scala World 2017 25 / 67

    View Slide

  36. Composing programs
    def zipFunction[A, B, X]
    (f: X => A, g: X => B): X => (A, B) =
    (x: X) => (f(x), g(x))
    Adelbert Chang (@adelbertchang) Simplicity in composition Scala World 2017 26 / 67

    View Slide

  37. Composing programs
    def zipFunction[A, B, X]
    (f: X => A, g: X => B): X => (A, B) =
    (x: X) => (f(x), g(x))
    def pureFunction[A, X](a: A): X => A =
    (_: X) => a
    Adelbert Chang (@adelbertchang) Simplicity in composition Scala World 2017 26 / 67

    View Slide

  38. /** Same as Applicative */
    trait Monoidal[F[_]] {
    def zip[A, B](fa: F[A], fb: F[B]): F[(A, B)]
    def pure[A](a: A): F[A]
    /*
    def map[A, B](fa: F[A])(f: A => B): F[B]
    */
    }
    Adelbert Chang (@adelbertchang) Simplicity in composition Scala World 2017 27 / 67

    View Slide

  39. User input Password reqs Features Latest posts
    Sign-up form Featured
    Welcome page
    Adelbert Chang (@adelbertchang) Simplicity in composition Scala World 2017 28 / 67

    View Slide

  40. Composing programs
    (F[A], F[B]) => F[(A, B)]
    Adelbert Chang (@adelbertchang) Simplicity in composition Scala World 2017 29 / 67

    View Slide

  41. Composing independent programs
    (F[A], F[B]) => F[(A, B)]
    Adelbert Chang (@adelbertchang) Simplicity in composition Scala World 2017 30 / 67

    View Slide

  42. Composing programs
    F[A]
    Adelbert Chang (@adelbertchang) Simplicity in composition Scala World 2017 31 / 67

    View Slide

  43. Composing dependent programs
    (F[A], A => F[B]) => F[B]
    Adelbert Chang (@adelbertchang) Simplicity in composition Scala World 2017 32 / 67

    View Slide

  44. Composing dependent programs
    F( ): type of program
    1>
    =
    >: (A → F(B) × B → F(C)) → A → F(C)
    Adelbert Chang (@adelbertchang) Simplicity in composition Scala World 2017 33 / 67

    View Slide

  45. Composing dependent programs
    F( ): type of program
    >
    >=: (F(A) × A → F(B)) → F(B)
    1>
    =
    >: (A → F(B) × B → F(C)) → A → F(C)
    Adelbert Chang (@adelbertchang) Simplicity in composition Scala World 2017 33 / 67

    View Slide

  46. Composing dependent programs
    F( ): type of program
    >
    >=: (F(A) × A → F(B)) → F(B)
    η : A → F(A)
    1>
    =
    >: (A → F(B) × B → F(C)) → A → F(C)
    Adelbert Chang (@adelbertchang) Simplicity in composition Scala World 2017 33 / 67

    View Slide

  47. Composing dependent programs
    F( ): type of program
    >
    >=: (F(A) × A → F(B)) → F(B)
    η : A → F(A)
    (fa >
    >= f ) >
    >= g = fa >
    >= (f >=> g)1
    1>
    =
    >: (A → F(B) × B → F(C)) → A → F(C)
    Adelbert Chang (@adelbertchang) Simplicity in composition Scala World 2017 33 / 67

    View Slide

  48. Composing dependent programs
    F( ): type of program
    >
    >=: (F(A) × A → F(B)) → F(B)
    η : A → F(A)
    (fa >
    >= f ) >
    >= g = fa >
    >= (f >=> g)1
    f (x) = η(x) >
    >= f
    1>
    =
    >: (A → F(B) × B → F(C)) → A → F(C)
    Adelbert Chang (@adelbertchang) Simplicity in composition Scala World 2017 33 / 67

    View Slide

  49. Composing dependent programs
    F( ): type of program
    >
    >=: (F(A) × A → F(B)) → F(B)
    η : A → F(A)
    (fa >
    >= f ) >
    >= g = fa >
    >= (f >=> g)1
    f (x) = η(x) >
    >= f
    fa = fa >
    >= η
    1>
    =
    >: (A → F(B) × B → F(C)) → A → F(C)
    Adelbert Chang (@adelbertchang) Simplicity in composition Scala World 2017 33 / 67

    View Slide

  50. Composing dependent programs
    def flatMapOption[A, B]
    (oa: Option[A], f: A => Option[B]): Option[B] =
    oa match {
    case Some(a) => f(a)
    case None => None
    }
    Adelbert Chang (@adelbertchang) Simplicity in composition Scala World 2017 34 / 67

    View Slide

  51. Composing dependent programs
    def flatMapList[A, B]
    (la: List[A], f: A => List[B]): List[B] =
    la match {
    case Nil => Nil
    case h :: t => f(h) ++ flatMapList(t, f)
    }
    Adelbert Chang (@adelbertchang) Simplicity in composition Scala World 2017 35 / 67

    View Slide

  52. Composing dependent programs
    def flatMapFunction[A, B, X]
    (fa: X => A, f: A => (X => B)): X => B =
    (x: X) => f(fa(x))(x)
    Adelbert Chang (@adelbertchang) Simplicity in composition Scala World 2017 36 / 67

    View Slide

  53. trait Monad[F[_]] {
    def flatMap[A, B](fa: F[A])(f: A => F[B]): F[B]
    def pure[A](a: A): F[A]
    }
    Adelbert Chang (@adelbertchang) Simplicity in composition Scala World 2017 37 / 67

    View Slide

  54. trait Monad[F[_]] extends Monoidal[F] {
    def flatMap[A, B](fa: F[A])(f: A => F[B]): F[B]
    def pure[A](a: A): F[A]
    }
    Adelbert Chang (@adelbertchang) Simplicity in composition Scala World 2017 38 / 67

    View Slide

  55. A nicer monad
    (fa >
    >= f ) >
    >= g = fa >
    >= (f >=> g)
    f (x) = η(x) >
    >= f
    fa = fa >
    >= η
    Adelbert Chang (@adelbertchang) Simplicity in composition Scala World 2017 39 / 67

    View Slide

  56. A nicer monad
    f : A → F(B)
    g : B → F(C)
    h : C → F(D)
    Adelbert Chang (@adelbertchang) Simplicity in composition Scala World 2017 40 / 67

    View Slide

  57. A nicer monad
    f : A → F(B)
    g : B → F(C)
    h : C → F(D)
    (f >=> g) >=> h = f >=> (g >=> h)
    Adelbert Chang (@adelbertchang) Simplicity in composition Scala World 2017 40 / 67

    View Slide

  58. A nicer monad
    f : A → F(B)
    g : B → F(C)
    h : C → F(D)
    (f >=> g) >=> h = f >=> (g >=> h)
    f = f >=> η = η >=> f
    Adelbert Chang (@adelbertchang) Simplicity in composition Scala World 2017 40 / 67

    View Slide

  59. User info Friends Cookies Logs
    Profile Recommendations
    News feed
    Adelbert Chang (@adelbertchang) Simplicity in composition Scala World 2017 41 / 67

    View Slide

  60. Category theory studies the algebra of composition.
    Adelbert Chang (@adelbertchang) Simplicity in composition Scala World 2017 42 / 67

    View Slide

  61. Category theory
    objects: A, B, C ...
    Adelbert Chang (@adelbertchang) Simplicity in composition Scala World 2017 43 / 67

    View Slide

  62. Category theory
    objects: A, B, C ...
    arrows: f : A → B, g : B → C ...
    Adelbert Chang (@adelbertchang) Simplicity in composition Scala World 2017 43 / 67

    View Slide

  63. Category theory
    objects: A, B, C ...
    arrows: f : A → B, g : B → C ...
    1A
    : A → A
    Adelbert Chang (@adelbertchang) Simplicity in composition Scala World 2017 43 / 67

    View Slide

  64. Category theory
    objects: A, B, C ...
    arrows: f : A → B, g : B → C ...
    1A
    : A → A
    (f ◦ g) ◦ h = f ◦ (g ◦ h)
    Adelbert Chang (@adelbertchang) Simplicity in composition Scala World 2017 43 / 67

    View Slide

  65. Category theory
    objects: A, B, C ...
    arrows: f : A → B, g : B → C ...
    1A
    : A → A
    (f ◦ g) ◦ h = f ◦ (g ◦ h)
    f = f ◦ 1A
    = 1A
    ◦ f
    Adelbert Chang (@adelbertchang) Simplicity in composition Scala World 2017 43 / 67

    View Slide

  66. Category theory
    B
    A C
    g
    1B
    f
    g◦f
    1A
    1C
    Adelbert Chang (@adelbertchang) Simplicity in composition Scala World 2017 44 / 67

    View Slide

  67. Category theory
    B
    A C
    g
    1B
    f
    g◦f
    1A
    1C
    Adelbert Chang (@adelbertchang) Simplicity in composition Scala World 2017 44 / 67

    View Slide

  68. Category theory
    B
    A C
    g
    1B
    f
    g◦f
    1A
    1C
    Adelbert Chang (@adelbertchang) Simplicity in composition Scala World 2017 44 / 67

    View Slide

  69. Category theory: monoids

    x
    y
    x⊕y
    1A
    Adelbert Chang (@adelbertchang) Simplicity in composition Scala World 2017 45 / 67

    View Slide

  70. Category theory: monoids

    x
    y
    x⊕y
    1A
    Adelbert Chang (@adelbertchang) Simplicity in composition Scala World 2017 45 / 67

    View Slide

  71. Category theory: monoids

    x
    y
    x⊕y
    1A
    Adelbert Chang (@adelbertchang) Simplicity in composition Scala World 2017 45 / 67

    View Slide

  72. Category theory: monoids

    x
    y
    x⊕y
    1A
    Adelbert Chang (@adelbertchang) Simplicity in composition Scala World 2017 45 / 67

    View Slide

  73. Category theory: monads
    Adelbert Chang (@adelbertchang) Simplicity in composition Scala World 2017 46 / 67

    View Slide

  74. Category theory: monads
    F(B)
    A F(C)
    f
    ?◦f
    Adelbert Chang (@adelbertchang) Simplicity in composition Scala World 2017 46 / 67

    View Slide

  75. Category theory: monads
    F(B)
    A F(C)
    f
    ?◦f
    >
    >=: (F(B) × B → F(C)) → F(C)
    Adelbert Chang (@adelbertchang) Simplicity in composition Scala World 2017 46 / 67

    View Slide

  76. Category theory: monads
    F(B)
    A F(C)
    f
    ?◦f
    >
    >=: (B → F(C)) → F(B) → F(C)
    Adelbert Chang (@adelbertchang) Simplicity in composition Scala World 2017 47 / 67

    View Slide

  77. Category theory: monads
    F(B)
    A F(C)
    g∗
    f
    g∗◦f
    >
    >=: (B → F(C)) → F(B) → F(C)
    Adelbert Chang (@adelbertchang) Simplicity in composition Scala World 2017 48 / 67

    View Slide

  78. Category theory: monads
    B
    A C
    g
    1B
    B→F(B)
    f
    g ◦f
    1A
    A→F(A) 1C
    C→F(C)
    Adelbert Chang (@adelbertchang) Simplicity in composition Scala World 2017 49 / 67

    View Slide

  79. Category theory: monads
    B
    A C
    g
    1B
    B→F(B)
    f
    g ◦f
    1A
    A→F(A) 1C
    C→F(C)
    Adelbert Chang (@adelbertchang) Simplicity in composition Scala World 2017 49 / 67

    View Slide

  80. Category theory: monads
    B
    A C
    g
    1B
    B→F(B)
    f
    g ◦f
    1A
    A→F(A) 1C
    C→F(C)
    Adelbert Chang (@adelbertchang) Simplicity in composition Scala World 2017 49 / 67

    View Slide

  81. Category theory: monads
    B
    A C
    g
    1B
    B→F(B)
    f
    g ◦f
    1A
    A→F(A) 1C
    C→F(C)
    η : X → F(X)
    Adelbert Chang (@adelbertchang) Simplicity in composition Scala World 2017 49 / 67

    View Slide

  82. User info Friends Cookies Logs
    Profile Recommendations
    News feed
    Adelbert Chang (@adelbertchang) Simplicity in composition Scala World 2017 50 / 67

    View Slide

  83. What if we have different monoids, monads, etc?
    Adelbert Chang (@adelbertchang) Simplicity in composition Scala World 2017 51 / 67

    View Slide

  84. (Monoid[A], Monoid[B]) => Monoid[?]
    Adelbert Chang (@adelbertchang) Simplicity in composition Scala World 2017 52 / 67

    View Slide

  85. Product composition: monoids
    (Monoid[A], Monoid[B]) => Monoid[(A, B)]
    Adelbert Chang (@adelbertchang) Simplicity in composition Scala World 2017 53 / 67

    View Slide

  86. Product composition: monoids
    def combine(x: (A, B), y: (A, B)): (A, B) = {
    val a = x._1 combine y._1
    val b = x._2 combine y._2
    (a, b)
    }
    0Assuming Monoid[A] and Monoid[B]
    Adelbert Chang (@adelbertchang) Simplicity in composition Scala World 2017 54 / 67

    View Slide

  87. Product composition: monoids
    def combine(x: (A, B), y: (A, B)): (A, B) = {
    val a = x._1 combine y._1
    val b = x._2 combine y._2
    (a, b)
    }
    def empty: (A, B) = (empty[A], empty[B])
    0Assuming Monoid[A] and Monoid[B]
    Adelbert Chang (@adelbertchang) Simplicity in composition Scala World 2017 54 / 67

    View Slide

  88. (Monoidal[F], Monoidal[G]) => Monoidal[?]
    Adelbert Chang (@adelbertchang) Simplicity in composition Scala World 2017 55 / 67

    View Slide

  89. Product composition: lax monoidal functors
    type L[X] = (F[X], G[X])
    (Monoidal[F], Monoidal[G]) => Monoidal[L]
    Adelbert Chang (@adelbertchang) Simplicity in composition Scala World 2017 56 / 67

    View Slide

  90. Product composition: lax monoidal functors
    def zip[A, B](x: (F[A], G[A]),
    y: (F[B], G[B])): (F[(A, B)], G[(A, B)]) = {
    val f = x._1 zip y._1
    val g = x._2 zip y._2
    (f, g)
    }
    0Assuming Monoidal[F] and Monoidal[G]
    Adelbert Chang (@adelbertchang) Simplicity in composition Scala World 2017 57 / 67

    View Slide

  91. Product composition: lax monoidal functors
    def zip[A, B](x: (F[A], G[A]),
    y: (F[B], G[B])): (F[(A, B)], G[(A, B)]) = {
    val f = x._1 zip y._1
    val g = x._2 zip y._2
    (f, g)
    }
    def pure[A](a: A): (F[A], G[A]) = (a.pure[F], a.pure[G])
    0Assuming Monoidal[F] and Monoidal[G]
    Adelbert Chang (@adelbertchang) Simplicity in composition Scala World 2017 57 / 67

    View Slide

  92. Product composition: monads
    type L[X] = (F[X], G[X])
    (Monad[F], Monad[G]) => Monad[L]
    Adelbert Chang (@adelbertchang) Simplicity in composition Scala World 2017 58 / 67

    View Slide

  93. Product composition: monads
    def flatMap[A, B]
    (xa: (F[A], G[A]))(ff: A => (F[B], G[B])):
    (F[(A, B)], G[(A, B)]) = {
    val f = xa._1.flatMap(a => ff(a)._1)
    val g = xa._2.flatMap(a => ff(a)._2)
    (f, g)
    }
    0Assuming Monad[F] and Monad[G]
    Adelbert Chang (@adelbertchang) Simplicity in composition Scala World 2017 59 / 67

    View Slide

  94. Nested composition: lax monoidal functors
    type L[X] = F[G[X]]
    (Monoidal[F], Monoidal[G]) => Monoidal[L]
    Adelbert Chang (@adelbertchang) Simplicity in composition Scala World 2017 60 / 67

    View Slide

  95. User input Password reqs Features Latest posts
    Sign-up form Featured
    Welcome page
    Adelbert Chang (@adelbertchang) Simplicity in composition Scala World 2017 61 / 67

    View Slide

  96. Nested composition: lax monoidal functors
    def zip[A, B](fga: F[G[A]], fgb: F[G[B]]): F[G[(A, B)]] = {
    val fp: F[(G[A], G[B])] = fga zip fgb
    fp.map { case (ga, gb) => ga zip gb }
    }
    0Assuming Monoidal[F] and Monoidal[G]
    Adelbert Chang (@adelbertchang) Simplicity in composition Scala World 2017 62 / 67

    View Slide

  97. Nested composition: lax monoidal functors
    def zip[A, B](fga: F[G[A]], fgb: F[G[B]]): F[G[(A, B)]] = {
    val fp: F[(G[A], G[B])] = fga zip fgb
    fp.map { case (ga, gb) => ga zip gb }
    }
    def pure[A](a: A): F[G[A]] =
    a.pure[G].pure[F]
    0Assuming Monoidal[F] and Monoidal[G]
    Adelbert Chang (@adelbertchang) Simplicity in composition Scala World 2017 62 / 67

    View Slide

  98. Nested composition: monads
    type L[X] = F[G[X]]
    (Monad[F], Monad[G]) => Monad[L]
    Adelbert Chang (@adelbertchang) Simplicity in composition Scala World 2017 63 / 67

    View Slide

  99. Nested composition: monads
    type L[X] = F[G[X]]
    (Monad[F], Monad[G]) => Monad[L]
    Adelbert Chang (@adelbertchang) Simplicity in composition Scala World 2017 64 / 67

    View Slide

  100. Nested composition: monads
    def flatMap[A, B](fga: F[G[A]](f: A => F[G[B]]): F[G[B]] =
    0Assuming Monad[F] and Monad[G]
    Adelbert Chang (@adelbertchang) Simplicity in composition Scala World 2017 65 / 67

    View Slide

  101. Nested composition: monads
    def flatMap[A, B](fga: F[G[A]](f: A => F[G[B]]): F[G[B]] =
    fga.flatMap { (ga: G[A]) =>
    ???
    }
    0Assuming Monad[F] and Monad[G]
    Adelbert Chang (@adelbertchang) Simplicity in composition Scala World 2017 65 / 67

    View Slide

  102. Review
    Associative composition allows for modular decomposition and
    reasoning
    Adelbert Chang (@adelbertchang) Simplicity in composition Scala World 2017 66 / 67

    View Slide

  103. Review
    Associative composition allows for modular decomposition and
    reasoning
    Monoids compose A’s, lax monoidal/applicative functors compose
    independent programs, monads compose dependent programs
    Adelbert Chang (@adelbertchang) Simplicity in composition Scala World 2017 66 / 67

    View Slide

  104. Review
    Associative composition allows for modular decomposition and
    reasoning
    Monoids compose A’s, lax monoidal/applicative functors compose
    independent programs, monads compose dependent programs
    Category theory studies composition, and each of the above can
    be framed as a category
    Adelbert Chang (@adelbertchang) Simplicity in composition Scala World 2017 66 / 67

    View Slide

  105. Review
    Associative composition allows for modular decomposition and
    reasoning
    Monoids compose A’s, lax monoidal/applicative functors compose
    independent programs, monads compose dependent programs
    Category theory studies composition, and each of the above can
    be framed as a category
    Monoids compose
    Adelbert Chang (@adelbertchang) Simplicity in composition Scala World 2017 66 / 67

    View Slide

  106. Review
    Associative composition allows for modular decomposition and
    reasoning
    Monoids compose A’s, lax monoidal/applicative functors compose
    independent programs, monads compose dependent programs
    Category theory studies composition, and each of the above can
    be framed as a category
    Monoids compose
    Lax monoidal/applicative functors compose
    Adelbert Chang (@adelbertchang) Simplicity in composition Scala World 2017 66 / 67

    View Slide

  107. Review
    Associative composition allows for modular decomposition and
    reasoning
    Monoids compose A’s, lax monoidal/applicative functors compose
    independent programs, monads compose dependent programs
    Category theory studies composition, and each of the above can
    be framed as a category
    Monoids compose
    Lax monoidal/applicative functors compose
    Monads in general do not compose
    See: monad transformers, extensible (algebraic) effects
    Adelbert Chang (@adelbertchang) Simplicity in composition Scala World 2017 66 / 67

    View Slide

  108. References
    Equational reasoning at scale - Gabriel Gonzalez
    http://www.haskellforall.com/2014/07/
    equational-reasoning-at-scale.html
    Invariant Shadows - Michael Pilquist
    http://mpilquist.github.io/blog/2015/06/22/
    invariant-shadows-part-2/
    All About Applicative - Me!
    https://www.youtube.com/watch?v=Mn7BtPALFys
    A categorial view of computational effects - Emily Riehl
    https://www.youtube.com/watch?v=6t6bsWVOIzs
    Conceptual Mathematics - F. William Lawvere and Stephen H.
    Schanuel
    Adelbert Chang (@adelbertchang) Simplicity in composition Scala World 2017 67 / 67

    View Slide