kb84tkhrのブログ

何を書こうか考え中です あ、あと組織とは関係ないってやつです 個人的なやつ

PEP 483を読む(続き2)

 

総称型(Generic types)

上で定義された基本的なビルディングブロックにより、ジェネリックな形で新しい型を構築することが可能となります。たとえば、Tupleはfloatを取って具体型Vector=Tuple[float, ...]になり、また、UserIDを取って別の具体型Registry=Tuple[UserID, ...]になります。そのような意味論は総称型コンストラクタとして知られています。関数の意味論に似ていますが、関数が値をとって値を返すのに対し、総称型コンストラクタはタイプを取ってタイプを「返し」ます。

タイプをとってタイプを返す
なるほどそういう風に考えるわけか

ところでsemanticsって訳しにくくないですか
Longmanさんによると

  1. the study of the meaning of words and phrases
  2. the meaning of a word

ということなので結局のところ言葉の意味ってことなんでしょうけど
この業界というか言語界隈では意味論って訳されてますな
意味論っていうときは1.の方かな

ある型や関数がそのような総称型的ふるまいをすることはよくあることです。

  • listやdictのようなコンテナクラスは通常、特定の型の値のみを含みます。したがって、users = [] # type: List[UserID]examples = {} # type: Dict[str, Any]のようにアノテートできます。
  • def add(x, y): return x + yのような関数は、intとintをとってintを返し、floatとfloatをとってfloatを返します。

ひとつめのような例を型でアノテートできるようにするには、組み込みのコンテナや抽象基底クラスを型パラメータで拡張できるようにして、それらが総称型コンストラクタとしてふるまうようにします。総称型コンストラクタとしてふるまうクラスを総称型と呼びます。

総称型だらけでなにがなんだか

from typing import Iterable

class Task:
  ...

def work(todo_list: Iterable[Task]) -> None:
  ...

この例ではIterableが総称型で、
具体型Taskをとって具体型Iterable[Task]を返します。

やってることは別に難しくはない

ふたつめの例のように、総称的にふるまう関数を総称関数と呼びます。
総称関数の型アノテーションは型変数によって可能となります。

さっきは型パラメータと言っていたけれども使い分けがあるんだろうか
総称クラスは型パラメータを取り、総称関数は型変数を取る、みたいな
違うものなのか単なる表記揺れなのか

総称型の意味論は関数のパラメータの意味論と似ているところはあるけれども
型変数に具体型を代入することはなく、
可能な値を見つけたり、見つからなかったときに警告を出すのは
静的タイプチェッカーの仕事

「型変数に具体型を代入することはなく」はPython本体が、ということかなあ
それともTがintになるときは代入ではないことが起こっているということなのか
わからない

型変数は型アノテーションでよく使われるだけでなく、型チェッカーの内部の型推論機は構築する基礎にもなります。

型推論ってたいへんだねえ