Slide 1

Slide 1 text

type-challenges を全問解いたので エッセンスと推し問題を紹介してみる TS Kaigi Hokuriku 2025 @kakekakemiya

Slide 2

Slide 2 text

© Knowledge Work Inc. ⾃⼰紹介 2 @kakekakemiya 株式会社ナレッジワーク 新卒 フロントエンドエンジニア フロントエンドと焼き⿃が好きです (初登壇で⼤変緊張しています...)

Slide 3

Slide 3 text

© Knowledge Work Inc. みなさん、TypeScript の型パズルはお好きですか!?✋ 突然ですが... 3

Slide 4

Slide 4 text

© Knowledge Work Inc. 型パズル:特定の条件を満たす独⾃のユーティリティ型を作るパズル 型パズル 4

Slide 5

Slide 5 text

© Knowledge Work Inc. 型パズル:特定の条件を満たす独⾃のユーティリティ型を作るパズル → 型パズル‧型システムに詳しくなると何が嬉しい? 型パズル 5

Slide 6

Slide 6 text

© Knowledge Work Inc. その1:複雑な型が「読める」 型パズルに詳しいと何が嬉しい? 6

Slide 7

Slide 7 text

© Knowledge Work Inc. 型パズルに詳しいと何が嬉しい? 7

Slide 8

Slide 8 text

© Knowledge Work Inc. その2:欲しい型が「書ける」 型パズルに詳しいと何が嬉しい? 8

Slide 9

Slide 9 text

© Knowledge Work Inc. ネストされたオブジェクトの プロパティを全部 required にしたいな... 型パズルに詳しいと何が嬉しい? 9 アプリ内のページの情報を型レベルで 管理したいな... snake_case を camelCase に変換したいな... 関数の引数‧返り値の型を うまく取り出したいな... 2つのオブジェクト型のプロパティの差を 取得したいな ※もちろん、メンテナンス性と旨味のバランスを考える必要はあります

Slide 10

Slide 10 text

© Knowledge Work Inc. 型パズルは便利で⾯⽩いが、慣れが⼤切 でも、意外と向き合う場⾯が少ない... 型パズルに詳しくなるには? 10

Slide 11

Slide 11 text

© Knowledge Work Inc. 型パズルは便利で⾯⽩いが、慣れが⼤切 でも、意外と向き合う場⾯が少ない... → そこで有⽤なのが type-challenges !! 型パズルに詳しくなるには? 11

Slide 12

Slide 12 text

© Knowledge Work Inc. type-challenges 12 https://github.com/type-challenges/type-challenges/blob/main/README.ja.md より

Slide 13

Slide 13 text

© Knowledge Work Inc. type-challenges 13 https://github.com/type-challenges/type-challenges/blob/main/README.ja.md より

Slide 14

Slide 14 text

© Knowledge Work Inc. type-challenges 14 https://github.com/type-challenges/type-challenges/blob/main/README.ja.md より 13問(+ お試し問題1問) 初級 103問 中級 55問 上級 17問 最上級

Slide 15

Slide 15 text

© Knowledge Work Inc. type-challenges 15 https://github.com/type-challenges/type-challenges/blob/main/README.ja.md より type-challenges には たくさん良質な問題があるが... ● 初学者が気軽に取り組むには 問題数が多い! ● easy でも結構難しい

Slide 16

Slide 16 text

© Knowledge Work Inc. type-challenges 16 https://github.com/type-challenges/type-challenges/blob/main/README.ja.md より type-challenges には たくさん良質な問題があるが... ● 初学者が気軽に取り組むには 問題数が多い! ● easy でも結構難しい → 全問題に取り組んで学んだ、 型パズルのエッセンスと推し問題を 紹介します!!

Slide 17

Slide 17 text

© Knowledge Work Inc. まずはお試し!! Hello World #13(# は問題番号) お試し問題 17

Slide 18

Slide 18 text

© Knowledge Work Inc. 初級編 初級編 18

Slide 19

Slide 19 text

© Knowledge Work Inc. 最初の問題! Pick #4 初級編 19

Slide 20

Slide 20 text

© Knowledge Work Inc. ジェネリクスに extends をつけると型に制約を設けられる MyType Object 型に対して keyof を利⽤すると property の union を取得できる エッセンス 20

Slide 21

Slide 21 text

© Knowledge Work Inc. 公式による Pick の実装 も同じ 余談 21

Slide 22

Slide 22 text

© Knowledge Work Inc. 学びの多い良問!! First of Array #14 初級編 22

Slide 23

Slide 23 text

© Knowledge Work Inc. 初級編 23

Slide 24

Slide 24 text

© Knowledge Work Inc. 初級編 24 この問題はこれで OK だが、↓のような問題だとどうなるか? ● Second: ⼆つ⽬の要素を取得する ● Last: 最後の要素を取得する

Slide 25

Slide 25 text

© Knowledge Work Inc. 初級編 25 infer を使って、好きなところの型を推論してもらう → よりスマートに所望の部分の型を取り出せる!!

Slide 26

Slide 26 text

© Knowledge Work Inc. 初級編 26 infer を利⽤することで複雑な三項演算のネストを避けられる!!

Slide 27

Slide 27 text

© Knowledge Work Inc. エッセンス 27 extends による型の三項演算は⾮常に重要 infer は「ここに⼊る型って何?」ってのを推論してくれる便利な機能 extends とともに利⽤する

Slide 28

Slide 28 text

© Knowledge Work Inc. ユーティリティ型である ReturnType などでも infer は利⽤されている 余談 28

Slide 29

Slide 29 text

© Knowledge Work Inc. 型パズルの必須テクを学ぶ! Awaited #189 初級編 29

Slide 30

Slide 30 text

© Knowledge Work Inc. 初級編 30

Slide 31

Slide 31 text

© Knowledge Work Inc. 初級編 31 Promise を外したものを次の Payload にして再帰している

Slide 32

Slide 32 text

© Knowledge Work Inc. エッセンス 32 複雑な型パズルを解く上で、再帰的な型は必須テクニック infer と組み合わせて、次のジェネリクスに渡す型を組み⽴てる

Slide 33

Slide 33 text

© Knowledge Work Inc. 中級編 中級編 33

Slide 34

Slide 34 text

© Knowledge Work Inc. 知っていると便利な⽂字列の処理 #Trim 108 中級編 34

Slide 35

Slide 35 text

© Knowledge Work Inc. 中級編 35

Slide 36

Slide 36 text

© Knowledge Work Inc. 中級編 36 string に対しても infer を利⽤することができる!!

Slide 37

Slide 37 text

© Knowledge Work Inc. 中級編 37 string に対しても infer を利⽤することができる!! → Template Literal Types のおかげ

Slide 38

Slide 38 text

© Knowledge Work Inc. 中級編 38 Template Literal Types の例 ①

Slide 39

Slide 39 text

© Knowledge Work Inc. 中級編 39 Template Literal Types の例 ②

Slide 40

Slide 40 text

© Knowledge Work Inc. string に対しても infer を利⽤することができ、⽂字列の処理に便利 Template Literal Types は知っておくと表現⼒が広がる エッセンス 40

Slide 41

Slide 41 text

© Knowledge Work Inc. 型パズルの癖が詰まった難問 Permutation #296 中級編 41

Slide 42

Slide 42 text

© Knowledge Work Inc. 中級編 42

Slide 43

Slide 43 text

© Knowledge Work Inc. 中級編 43 まず、union の挙動について

Slide 44

Slide 44 text

© Knowledge Work Inc. 中級編 44 まず、union の挙動について

Slide 45

Slide 45 text

© Knowledge Work Inc. 中級編 45 まず、union の挙動について

Slide 46

Slide 46 text

© Knowledge Work Inc. 中級編 46 union の extends 適⽤時には分配則がはたらく (※分配則は算数でいうところの「a×(b + c) = a×b + a×c 」のイメージ)

Slide 47

Slide 47 text

© Knowledge Work Inc. 中級編 47 となると、Permutationをつくるなら

Slide 48

Slide 48 text

© Knowledge Work Inc. 中級編 48 となると、Permutationをつくるなら どうやって計算する...?(T はもう分配されてしまっている...)

Slide 49

Slide 49 text

© Knowledge Work Inc. 中級編 49 分配される T とは別に、分配前の T を保存する → K は extends されないので、分配が発⽣しない!! ということで、めでたしめでたし

Slide 50

Slide 50 text

© Knowledge Work Inc. 中級編 50 never の挙動について

Slide 51

Slide 51 text

© Knowledge Work Inc. 中級編 51 never の挙動について // never になる!!

Slide 52

Slide 52 text

© Knowledge Work Inc. 中級編 52 T extends … の T に never が渡ると、到達不能な union になり never が返る 先ほどの↓でも、再帰の最後で never を extends してしまっていた 参考:https://github.com/microsoft/TypeScript/issues/23182#issuecomment-379094672

Slide 53

Slide 53 text

© Knowledge Work Inc. 中級編 53 なので、never が渡ってきた際の extends を防いであげると OK

Slide 54

Slide 54 text

© Knowledge Work Inc. エッセンス 54 union に対して extends を利⽤すると、分配則が適⽤される never はジェネリクスとして extends されると、到達不能だと解釈される → 型引数の利⽤や [] での wrap など、分配をうまく制御するのが重要

Slide 55

Slide 55 text

© Knowledge Work Inc. 上級‧最上級編 上級‧最上級編 55

Slide 56

Slide 56 text

© Knowledge Work Inc. これぞパズル IsAny #223 上級‧最上編 56

Slide 57

Slide 57 text

© Knowledge Work Inc. 上級‧最上級編 57 Any の判定ってどうやるんだろう...

Slide 58

Slide 58 text

© Knowledge Work Inc. 上級‧最上級編 58 Any の判定ってどうやるんだろう...

Slide 59

Slide 59 text

© Knowledge Work Inc. 上級‧最上級編 59

Slide 60

Slide 60 text

© Knowledge Work Inc. エッセンス 60 型パズル上で交差型が利⽤できると痒いところに⼿が届くことがある Union to Intersection #55 なども類題としておすすめ

Slide 61

Slide 61 text

© Knowledge Work Inc. 型でこんなこともできる! Subtract #7561 上級‧最上編 61

Slide 62

Slide 62 text

© Knowledge Work Inc. 上級‧最上編 62 type-challenges では、数字を扱う問題も存在 最終的には、⾜し算‧引き算‧掛け算を実装 Subtract はこの中では⼀番シンプルで学びが多い

Slide 63

Slide 63 text

© Knowledge Work Inc. 上級‧最上編 63

Slide 64

Slide 64 text

© Knowledge Work Inc. 上級‧最上編 64 数字を扱うときは配列を利⽤する!!

Slide 65

Slide 65 text

© Knowledge Work Inc. 上級‧最上編 65 ⻑さ N の配列の型を作る

Slide 66

Slide 66 text

© Knowledge Work Inc. 上級‧最上編 66 A の配列 = [...Bの配列, infer 残り] とする

Slide 67

Slide 67 text

© Knowledge Work Inc. 上級‧最上編 67 残りの配列の⻑さを取得

Slide 68

Slide 68 text

© Knowledge Work Inc. 上級‧最上編 68 数字など複雑な型を扱うときの注意点

Slide 69

Slide 69 text

© Knowledge Work Inc. 上級‧最上編 69 エラーを期待している

Slide 70

Slide 70 text

© Knowledge Work Inc. 上級‧最上編 70 Type instantiation is excessively deep and possibly infinite.(2589) というエラーが発⽣ → 再帰回数の上限に到達して、型エラーとなる

Slide 71

Slide 71 text

© Knowledge Work Inc. エッセンス 71 型レベルで数字を扱いたい場合は、配列を利⽤するのが鉄則 複雑な型を作るときは、再帰回数の上限に注意!

Slide 72

Slide 72 text

© Knowledge Work Inc. 最後に 72 今⽇の発表によって ● TypeScript の型がより好きになった ● 型パズルに興味が沸いた ⽅がいらっしゃると幸いです!

Slide 73

Slide 73 text

© Knowledge Work Inc. 最後に 73 ↑から⾶べます!