Slide 1

Slide 1 text

ݍ࿦ͱɹɹɹ Swift΁ͷԠ༻ 2018/09/02 iOSDC 2018 Yasuhiro Inami / @inamiy

Slide 2

Slide 2 text

No content

Slide 3

Slide 3 text

No content

Slide 4

Slide 4 text

ݍ࿦ Category Theory

Slide 5

Slide 5 text

No content

Slide 6

Slide 6 text

ݍ࿦ͱ͸ʁ • ʮ఺ʯͱʮ໼ҹʯΛ࢖ͬͨ਺ֶͷ Foundation.framework • ఺ΑΓ΋໼ҹͷํ͕ॏཁʢू߹࿦ͷߟ͑ํͱ͸ٯʣ • Ԡ༻ൣғ͕޿͍ɿ ਺ֶɺ࿦ཧֶɺܭࢉػՊֶɺཧ࿦෺ཧֶɺ ೝ஌Պֶɺ఩ֶɺੜ෺ֶɺetc • ਺ֶͷ஌͕ࣝθϩͰ΋ֶ΂Δʢඍੵɺઢܗ୅਺΋͍Βͳ͍ʣ • ؔ਺ܕϓϩάϥϛϯάͰେ׆༂

Slide 7

Slide 7 text

ݍ࿦ΛֶͿ → ܕγεςϜ νϣοτσΩϧ • ࠶ؼܕʢෆಈ఺ɺfixɺreduce (fold) / sequence (unfold)ʣ • શশྔԽ ʢύϥϝʔλଟ૬ɺδΣωϦΫεʣ • ଘࡏྔԽ ʢϓϩτίϧ (existential container)ʣ • ߴϥϯΫଟ૬ʢଟ૬ؔ਺ΛҾ਺ͱͯ͠࢖͑Δʣ • ߴΧΠϯυଟ૬ʢܕίϯετϥΫλΛܕҾ਺ͱͯ͠࢖͑Δʣ • ґଘܕʢ஋ʹґଘ͢Δܕ͕࡞ΕΔʣ

Slide 8

Slide 8 text

ݍ࿦ΛֶͿ ↓ ʮܕʯΛ ΑΓਂ͘ཧղͰ͖Δ ↓ Swiftͷݱঢ়ͱ ະདྷ͕ݟ͑ͯ͘Δ

Slide 9

Slide 9 text

※ ͓அΓ ͜ͷεϥΠυͰ͸ɺ ʮٙࣅSwiftʯΛ࢖ͬͯղઆ͍ͯ͠·͢ɻ ( Swift 4.2ݱࡏɺݴޠػೳ͕଍Γͳ͍ͨΊ)

Slide 10

Slide 10 text

ݍͷఆٛ Definition

Slide 11

Slide 11 text

No content

Slide 12

Slide 12 text

No content

Slide 13

Slide 13 text

No content

Slide 14

Slide 14 text

No content

Slide 15

Slide 15 text

No content

Slide 16

Slide 16 text

No content

Slide 17

Slide 17 text

No content

Slide 18

Slide 18 text

No content

Slide 19

Slide 19 text

No content

Slide 20

Slide 20 text

No content

Slide 21

Slide 21 text

ݍͷఆٛ • ର৅ (object)ɿ • ࣹ (morphism)ɿ • ߃౳ࣹ (identity)ɿ • ߹੒ (composition)ɿ • ݁߹཯ (associativity)ɿ • ࢝Ҭ (domain) / ऴҬ (codomain):

Slide 23

Slide 23 text

ؔख Functor

Slide 24

Slide 24 text

No content

Slide 25

Slide 25 text

No content

Slide 26

Slide 26 text

No content

Slide 27

Slide 27 text

No content

Slide 28

Slide 28 text

No content

Slide 29

Slide 29 text

No content

Slide 30

Slide 30 text

No content

Slide 31

Slide 31 text

ؔख (Functor) • ݍΛʮର৅ʯʹɺ ͋Δݍ͔Β͋Δݍ ΁ͷߏ଄ʢ໼ҹશମͷܗʣΛอͭ ʮࣹʯʢϚοϐϯάʣ • ֤ର৅ ʹ͍ͭͯ ʹରԠ • ֤ࣹ ʹ͍ͭͯ ʹରԠ • ߏ଄ʢ߹੒ͱ߃౳ࣹʣΛอଘ͢Δ • •

Slide 32

Slide 32 text

// ٙࣅSwift protocol Functor[F] { // Note: `self.map { ... }` ʢΠϯελϯεϝιουʣ // ͱͯ͠΋࢖͑Δͱ͢Δ static func map(_ self: F, _ f: A -> B) -> F } extension Functor[Array] { ... } // ࢖༻ྫɿ Array ==> Array [1, 2, 3].map(String.init) == ["1", "2", "3"]

Slide 33

Slide 33 text

ؔखͱ͸ʮmap ͕Ͱ͖Δʯ͜ͱ map = ίϯςφΛม͑ͣʹ த਎Λม͑Δʁ ʢର৅͕த৺ (pointwise) ͷߟ͑ํʣ

Slide 35

Slide 35 text

No content

Slide 36

Slide 36 text

map ʢؔखʣ͸ɾɾɾ ݍͷؔ਺ f Λɺผͷݍͷؔ਺ F(f) = map(f) ʹࣸ͢ ʢࣹ͕த৺ (pointfree) ͷߟ͑ํʣ

Slide 37

Slide 37 text

ͷҙຯ 2ͭͷࣹ ʹ͍ͭͯɺઌʹ߹੒͔ͯ͠Β Λద༻ͯ͠΋ɺ ΛͦΕͧΕʹద༻͔ͯ͠Β߹੒ͯ͠΋ಉ͡

Slide 38

Slide 38 text

ͷྫ let count: String -> Int = { $0.count } let isEven: Int -> Bool = { $0 % 2 == 0 } ["Hello"].map(isEven ⚬ count) // ؔ਺߹੒ ʴ 1ճ `map` == ["Hello"].map(count).map(isEven) // 2ճ `map` // ==> F.map(isEven ⚬ count) == F.map(isEven) ⚬ F.map(count) ! 2ճ map͸ɺʮؔ਺߹੒ʴ1ճ mapʯͱಉ͡ʢܭࢉྔ࡟ݮʣ

Slide 39

Slide 39 text

༨ஊɿࣗݾؔख (Endofunctor) ͜͜·Ͱɺ Array ΍ Array Λɺ Int ΍ String ͱ͸ ผͷݍʢArray ͷݍʣ ͷର৅ͱͯ͠ߟ͖͑ͯͨ ɹɹɹɹɹɹɹɹɹɹɹɹɹˣ ࣮ࡍ͸ɺ͢΂ͯಉ͡SwiftͷܕͳͷͰɺ1ͭͷʮSwiftݍ ʯͷର৅ ͱͯ͠ѻͬͯྑ͍ ɹɹɹɹɹɹɹɹɹɹɹɹɹˣ ϓϩάϥϛϯάͷੈքͷ ؔख (Functor) ͱ͸ɺ࣮͸ ࣗݾؔख ʢݍ͔Βಉ͡ݍ΁ͷؔख ʹ ଟ૬ؔ਺ mapʣ ͷ͜ͱ

Slide 40

Slide 40 text

No content

Slide 41

Slide 41 text

ࣗવม׵ Natural Transformation

Slide 42

Slide 42 text

No content

Slide 43

Slide 43 text

No content

Slide 44

Slide 44 text

No content

Slide 45

Slide 45 text

ࣗવม׵ • 2ͭͷݍͷؒͷ"ࣹ"Ͱ͋ΔؔखΛʮର ৅ʯͱͯ͠ѻͬͨͱ͖ͷɺؔख͔Β ؔख΁ͷʮࣹʯ • ݍ ͱؔख ͕༩͑ ΒΕͨͱ͖ɺࣗવม׵ ͸ ͷࣹ ͷू߹ Ͱɺ೚ҙͷ ʹରͯ͠ɺҎ Լͷ౳ࣜʢՄ׵ਤࣜʣ Λຬͨ͢ɿ

Slide 48

Slide 48 text

ถాͷิ୊ Yoneda Lemma

Slide 49

Slide 49 text

No content

Slide 50

Slide 50 text

No content

Slide 51

Slide 51 text

No content

Slide 52

Slide 52 text

No content

Slide 53

Slide 53 text

No content

Slide 54

Slide 54 text

No content

Slide 55

Slide 55 text

ถాͷิ୊

Slide 58

Slide 58 text

ࢀߟεϥΠυ2ɿ ಉܕͷ࿩ 2 https://speakerdeck.com/inamiy/algebraic-data-type-in-swift ༨ஊɿถాͷิ୊Λ࢖͏ͱ ͷࢦ਺๏ଇ΍ɺ෼഑๏ଇͳͲ͕؆୯ʹূ໌Ͱ͖·͢

Slide 59

Slide 59 text

ถాͷิ୊͔Βɺܧଓ (CPS) ͱCPSม׵ • ʢ߃౳ؔखʣͱ͓͘ͱɺCPSʢܧଓʣ • ͱ͓͘ͱɺCPSม׵ʢʹ ถాຒΊࠐΈ ʣ func cpsTransform(_ f: X -> A) -> (A -> B) -> (X -> B) { return { aToB in return { x in aToB(f(x)) } } }

Slide 60

Slide 60 text

func fac(_ n: Int) -> Int { // ⚠ ຤ඌ࠶ؼͷܗͰ͸ͳ͍ʢ͕ɺཪͰίϯύΠϥ͕࠷దԽͯ͘͠ΕΔʣ return n == 0 ? 1 : n * fac (n - 1) } // `cpsTransform` Λ࢖Θͣɺखॻ͖ͰܧଓʹΑΔ຤ඌ࠶ؼ func facCPS(_ n: Int, _ next: Int -> R) -> R { return n == 0 ? next(1) : facCPS(n - 1, { next(n * $0) }) } // `cpsTransform` Λ࢖ͬͨ৔߹ʢ຤ඌ࠶ؼ࠷దԽʣ let facCPSAuto: (Int -> Int) -> Int -> Int = cpsTransform(fac) facCPS(4, id) // 24 ʢखಈͰ຤ඌ࠷దʣ facCPSAuto(id)(4) // 24 ʢࣗಈͰ຤ඌ࠷దʣ

Slide 61

Slide 61 text

ਵ൐ Adjunction

Slide 62

Slide 62 text

No content

Slide 63

Slide 63 text

No content

Slide 64

Slide 64 text

No content

Slide 65

Slide 65 text

ਵ൐

Slide 66

Slide 66 text

ࣗ༝ؔख ๨٫ؔख

Slide 67

Slide 67 text

// ٙࣅSwift protocol Adjunction[F, U] where Functor[F], Functor[U] { /// (F(C) -> D) -> (C -> U(D)) static func leftAdjunct(_ f: F -> D) -> C -> U /// (C -> U(D)) -> (F(C) -> D) static func rightAdjunct(_ f: C -> U) -> F -> D }

Slide 68

Slide 68 text

Slide 72

Slide 72 text

leftAdjunct == curry rightAdjunct == uncurry (Tuple ⊣ Func ͷͱ͖)

Slide 73

Slide 73 text

ਵ൐ͷผͷఆٛ

Slide 74

Slide 74 text

No content

Slide 75

Slide 75 text

No content

Slide 76

Slide 76 text

No content

Slide 77

Slide 77 text

No content

Slide 78

Slide 78 text

No content

Slide 79

Slide 79 text

No content

Slide 80

Slide 80 text

extension Adjunction { static func unit(_ c: C) -> U> { // `leftAdjunct` ͷୈ1Ҿ਺͸ `F -> D` ͳͷͰɺ // `id` Λద༻͢Δͱɺܕͱͯ͠ `D = F` ͕֬ఆ͢Δ return leftAdjunct(id)(c) } static func counit(_ fud: F>) -> D { return rightAdjunct(id)(fud) } }

Slide 81

Slide 81 text

counit: F> -> D ʹɺ D = F Λ୅ೖͯ͠ΈΔͱ counit: F>> -> F ͜ΕΛ͞Βʹ ؔख U ͰϦϑτ͢Δͱ U.map(counit): U>>> -> U> extension Adjunction { static func join(_ x: U>>>) -> U> { return map(counit) } }

Slide 82

Slide 82 text

੔ཧͯ͠ΈΔɿ extension Adjunction { static func unit(_ c: C) -> U> { return leftAdjunct(id)(c) } static func join(_ x: U>>>) -> U> { return map(counit) } } ͜͜Ͱɺ U> = M ͱஔ͍ͯΈΔͱɾɾɾ

Slide 83

Slide 83 text

protocol Monad[M] where Functor[M] { static func unit(_ c: C) -> M static func join(_ mmc: M>) -> M } extension Monad { static func flatMap(_ f: C -> M) -> M -> M { return { (join ⚬ map(f))($0) } } }

Slide 84

Slide 84 text

Ϟφυ Monad

Slide 85

Slide 85 text

ਵ൐ ↓ Ϟφυ

Slide 86

Slide 86 text

ྫɿ Tuple ⊣ Func ΑΓɺ Func> ʹʮؔ਺ͷதʹλϓϧΛೖΕΔʯʹ ঢ়ଶϞφυ struct State { let runState: S -> (A, S) init(_ fun: Func>) { // `Func>` ͱ // `S -> (A, S)` ͸࣮͸ಉ͡ʂ self.runState = fun } }

Slide 87

Slide 87 text

͸Ϟφυ Ͱ͸ɺٯͷ ͸lĤĤĤ

Slide 88

Slide 88 text

// W ͸ Ϟφυ M ͷٯ protocol Comonad[W] where Functor[W] { // Ϟφυͷ `unit: C -> M` ͷٯ static func counit(_ wc: W) -> D // Ϟφυͷ `join: M> -> M` ͷٯ static func duplicate(_ wc: W) -> W> }

Slide 89

Slide 89 text

No content

Slide 90

Slide 90 text

༨Ϟφυ Comonad

Slide 91

Slide 91 text

ਵ൐ ↓ ༨Ϟφυ

Slide 94

Slide 94 text

Ϩϯζ͸ ༨ঢ়ଶ༨Ϟφυͷ ༨୅਺ Lenses are Costate Comonad Coalgebras

Slide 95

Slide 95 text

·ͱΊ • ݍɺ߹੒ɺ߃౳ࣹ • ؔख (Functor) → ݍͷࣹΛɺผͷݍʹࣸ͢ (map) • ࣗવม׵ (Natural Transformation) → Մ׵ਤࣜɺଟ૬ؔ਺ • ถాͷิ୊ (Yoneda Lemma) → ܧଓ (CPS) ͳͲ • ਵ൐ (Adjunction) → ΧϦʔԽɺϞφυɺ༨Ϟφυ • Ϟφυ / ༨Ϟφυ ((Co-)Monad) → ঢ়ଶϞφυɺϨϯζ

Slide 96

Slide 96 text

͞ΒʹֶͿͨΊʹ • ۃݶ (Limit) l ੵɺΠίϥΠβɺҾ͖໭͠ɺetc • Τϯυ / ༨Τϯυ (End / Coend) • ୅਺ / ༨୅਺ (Algebra / Coalgebra) • ࣗ༝ؔखɾࣗ༝Ϟφυ (Free Functor, Free Monad) • Χϯ֦ு (Kan Extension) • ϞϊΠυݍɾ๛য়ݍ (Monoidal / Enriched Category)

Slide 97

Slide 97 text

ࢀߟจݙʢॳֶऀ޲͚ʣ • Bartosz Milewski's Programming Cafe | Category Theory, Haskell, Concurrency, C++ • ! Bartosz Milewski - YouTube • ! TheCatsters - YouTube • Category theory for beginners • ݍ࿦ษڧձ @ ϫʔΫεΞϓϦέʔγϣϯζ

Slide 98

Slide 98 text

ࢀߟจݙʢதʙ্ڃऀ޲͚ʣ • ! ݍ࿦ ݪஶୈ2൛ | Steve Awodey • ! ϕʔγοΫݍ࿦ ීวੑ͔Βͷ଎शίʔε | Tom Leinster • ! ݍ࿦ͷجૅ | Saunders MacLane • ݍ࿦ | ұେ੔Ҭ • ᐻࢁਖ਼޾ͷΩϚΠϥࣂҭه • nLab

Slide 99

Slide 99 text

Thanks! Yasuhiro Inami @inamiy