🦁

Pythonで一部のキーが存在しない型を定義する

2024/06/29に公開

Python 3.8以降では、TypedDictを使用して辞書のキーとその値の型を定義することができます。
時には、キーが必須ではなく、オプショナルである(キーが存在しない)型を定義したい場合があります。

TypeScriptにおける次のような型をPythonで定義する方法を考えます。

type User = {
    name: string;
    email?: string;
}

Optionalでの実装例と問題点

Optionalを使用すると、キーは常に存在するが、値がNoneになる可能性を示します。
そのため、キーが存在することを前提とするコードでは問題が発生します。

from typing import TypedDict, Optional


class User(TypedDict):
    name: str
    email: Optional[str]


def hello(user: User):
    print(f"Hello, {user['name']}")
    # キーが存在しない可能性があるが、型チェックでエラーとならず実行時にエラーが発生する
    print(f"Your email is {user['email']}")

NotRequiredによる解決策

Python3.11以降であれば、NotRequiredを使用して特定のキーが存在しないことを示す型を定義できます。
これにより、キーの存在チェックをせずに参照している場合に型エラーが発生します。

from typing import TypedDict, NotRequired


class User(TypedDict):
    name: str
    email: NotRequired[str]


def hello(user: User):
    print(f"Hello, {user['name']}")
    # Could not access item in TypedDict "email" is not a required key in "User", so access may result in runtime exception
    print(f"Your email is {user['name']}")

まとめ

キーが任意で存在しない可能性がある型を定義したい場合は、NotRequiredを使用しましょう。

Discussion