Upgrade to Pro
— share decks privately, control downloads, hide ads and more …
Speaker Deck
Features
Speaker Deck
PRO
Sign in
Sign up for free
Search
Search
Python 3.13で進化したtype predicateについてと、タグ付きユニオンを使っ...
Search
nsuz
December 22, 2024
Programming
330
0
Share
Embed
Copy iframe code
Copy JS code
Copy link
Start on current slide
Python 3.13で進化したtype predicateについてと、タグ付きユニオンを使ったtype narrowingについて
Python札幌 シーズンX Vol.3 LT勉強会
発表資料
nsuz
December 22, 2024
More Decks by nsuz
See All by nsuz
「無ければ作る」Backlogに欲しい機能を自分で作った話
nsuz
0
1.6k
Other Decks in Programming
See All in Programming
Webフレームワークの ベンチマークについて
yusukebe
0
160
Spec-Driven Development with AI-Agents: From High-Level Requirements to Working Software
antonarhipov
2
490
タクシーアプリ『GO』の バックエンド開発のおける AI利活用と若者のすべて
pyama86
3
1.9k
Contextとはなにか
chiroruxx
0
280
Lemonade + Foundry Toolkit でお手軽アプリ開発
seosoft
1
320
「エンジニアインターン、どうやって取った?」準備のリアルを語るLT会 Progate BAR
akiomatic
0
130
Observability in Practice:Grafana 與 Edge Device SRE 的那些事
blueswen
0
160
Copilot CLI の継戦能力を高める コンテキスト管理
nozomutu
1
1.2k
例外の正しい扱い方 そのエラー try-catchして大丈夫?
jinwatanabe
0
200
IBM Bobを活用したレガシーアプリの最新化
oniak3ibm
PRO
1
190
スマートグラスで並列バイブコーディング
hyshu
0
120
Dataformのリポジトリを立ち上げるときにまずやること / dataform-day0-2026
snhryt
0
150
Featured
See All Featured
The AI Revolution Will Not Be Monopolized: How open-source beats economies of scale, even for LLMs
inesmontani
PRO
3
3.5k
Music & Morning Musume
bryan
47
7.2k
How to Grow Your eCommerce with AI & Automation
katarinadahlin
PRO
1
200
Agile Actions for Facilitating Distributed Teams - ADO2019
mkilby
0
200
A Soul's Torment
seathinner
6
2.9k
The Organizational Zoo: Understanding Human Behavior Agility Through Metaphoric Constructive Conversations (based on the works of Arthur Shelley, Ph.D)
kimpetersen
PRO
0
360
More Than Pixels: Becoming A User Experience Designer
marktimemedia
3
440
What's in a price? How to price your products and services
michaelherold
247
13k
Context Engineering - Making Every Token Count
addyosmani
9
960
Bash Introduction
62gerente
615
220k
Save Time (by Creating Custom Rails Generators)
garrettdimon
PRO
32
3.4k
Stewardship and Sustainability of Urban and Community Forests
pwiseman
0
220
Transcript
Python 3.13で進化したtype predicateについてと、タ グ付きユニオンを使ったtype narrowingについて 鈴木直柔 2024-12-23 Python札幌
自己紹介 鈴木直柔 (@nsuz) 株式会社 エクサウィザーズ ソフトウェアエンジニア
Python 3.13で進化したtype predicate
a: list[str | None] = ["foo", None, "bar", None, "baz"]
b = filter(lambda x: x is not None, a) c = map(lambda x: x.upper(), b)
None
type predicete function def is_not_none[T](x: T | None) -> TypeIs[T]:
return x is not None typing.TypeIs Python 3.13で追加された。TypeGuard(3.10~)の進化版。
None
TypeGuardから進化したポイント TypeGuardの課題
TypeGuardから進化したポイント TypeIs 型述語関数の返り値がTrueのとき、元の変数の型との交差型として推論されるよ うになった 型述語関数の返り値がFalseのときもnarrowingできるようになった
タグ付きユニオンを使ったtype narrowing
class Ok[T](TypedDict): type: Literal["ok"] value: T class Error(TypedDict): type: Literal["error"]
value: Exception type Result[T] = Ok[T] | Error def unwrap[T](result: Result[T]) -> T: if result["type"] == "ok": return result["value"] # result: Ok[T] else: raise result["value"] # result: Error
data: list[Result[int]] = [ {"type": "ok", "value": 42}, {"type": "error",
"value": ValueError("Something went wrong")}, ] for d in data: try: print(unwrap(d)) except Exception as e: print(f"Error!!!! {e}")
例えば・・・ APIレスポンスが、 成功時 { "result": 0, "data": ... } 失敗時
{ "result": 1, "error": ... } みたいなとき
from typing import Literal, TypedDict type Data = list[str] class
OkResponse(TypedDict): result: Literal[0] data: Data class ErrorResponse(TypedDict): result: Literal[1] error: str type Response = OkResponse | ErrorResponse def unwrap[T](res: Response) -> Data: if res["result"] == 0: return res["data"] else: raise Exception(res["error"]) data: list[Response] = [ {"result": 0, "data": ["foo", "bar", "baz"]}, {"result": 1, "error": "ERROR_CODE_123"}, ] for d in data: try: print(unwrap(d)) except Exception as e: print(f"Error!!!! {e}")
(ただ、Pythonの場合、内部でつくるデータについてはTypedDictでタグ付きユニオン をつくるよりも、dataclassなどでクラスにした方が、構造的パターンマッチングでス マートに扱えるかも・・?)
from dataclasses import dataclass @dataclass class Ok[T]: value: T @dataclass
class Error: value: Exception type Result[T] = Ok[T] | Error def unwrap[T](result: Result[T]) -> T: match result: case Ok(v): return v case Error(e): raise e
data: list[Result[int]] = [ Ok(42), Error(ValueError("Something went wrong")), ] for
d in data: try: print(unwrap(d)) except Exception as e: print(f"Error!!!! {e}")