Thanks to visit codestin.com
Credit goes to github.com

Skip to content

Commit e608709

Browse files
author
Guido van Rossum
committed
Expand documentation about type aliases and NewType in the typing module (merge 3.5 -> 3.6).
By Michael Lee.
2 parents c1f974c + 342e800 commit e608709

1 file changed

Lines changed: 96 additions & 1 deletion

File tree

Doc/library/typing.rst

Lines changed: 96 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -29,10 +29,105 @@ arguments.
2929
Type aliases
3030
------------
3131

32-
A type alias is defined by assigning the type to the alias::
32+
A type alias is defined by assigning the type to the alias. In this example,
33+
``Vector`` and ``List[float]`` will be treated as interchangeable synonyms::
3334

35+
from typing import List
3436
Vector = List[float]
3537

38+
def scale(scalar: float, vector: Vector) -> Vector:
39+
return [scalar * num for num in vector]
40+
41+
# typechecks; a list of floats qualifies as a Vector.
42+
new_vector = scale(2.0, [1.0, -4.2, 5.4])
43+
44+
Type aliases are useful for simplifying complex type signatures. For example::
45+
46+
from typing import Dict, Tuple, List
47+
48+
ConnectionOptions = Dict[str, str]
49+
Address = Tuple[str, int]
50+
Server = Tuple[Address, ConnectionOptions]
51+
52+
def broadcast_message(message: str, servers: List[Server]) -> None:
53+
...
54+
55+
# The static type checker will treat the previous type signature as
56+
# being exactly equivalent to this one.
57+
def broadcast_message(
58+
message: str,
59+
servers: List[Tuple[Tuple[str, int], Dict[str, str]]]) -> None:
60+
...
61+
62+
NewType
63+
-------
64+
65+
Use the ``NewType`` helper function to create distinct types::
66+
67+
from typing import NewType
68+
69+
UserId = NewType('UserId', int)
70+
some_id = UserId(524313)
71+
72+
The static type checker will treat the new type as if it were a subclass
73+
of the original type. This is useful in helping catch logical errors::
74+
75+
def get_user_name(user_id: UserId) -> str:
76+
...
77+
78+
# typechecks
79+
user_a = get_user_name(UserId(42351))
80+
81+
# does not typecheck; an int is not a UserId
82+
user_b = get_user_name(-1)
83+
84+
You may still perform all ``int`` operations on a variable of type ``UserId``,
85+
but the result will always be of type ``int``. This lets you pass in a
86+
``UserId`` wherever an ``int`` might be expected, but will prevent you from
87+
accidentally creating a ``UserId`` in an invalid way::
88+
89+
# `output` is of type `int`, not `UserId`
90+
output = UserId(23413) + UserId(54341)
91+
92+
Note that these checks are enforced only by the static type checker. At runtime
93+
the statement ``Derived = NewType('Derived', Base)`` will make ``Derived`` a
94+
function that immediately returns whatever parameter you pass it. That means
95+
the expression ``Derived(some_value)`` does not create a new class or introduce
96+
any overhead beyond that of a regular function call.
97+
98+
More precisely, the expression ``some_value is Derived(some_value)`` is always
99+
true at runtime.
100+
101+
This also means that it is not possible to create a subtype of ``Derived``
102+
since it is an identity function at runtime, not an actual type. Similarly, it
103+
is not possible to create another ``NewType`` based on a ``Derived`` type::
104+
105+
from typing import NewType
106+
107+
UserId = NewType('UserId', int)
108+
109+
# Fails at runtime and does not typecheck
110+
class AdminUserId(UserId): pass
111+
112+
# Also does not typecheck
113+
ProUserId = NewType('ProUserId', UserId)
114+
115+
See :pep:`484` for more details.
116+
117+
.. note::
118+
119+
Recall that the use of a type alias declares two types to be *equivalent* to
120+
one another. Doing ``Alias = Original`` will make the static type checker
121+
treat ``Alias`` as being *exactly equivalent* to ``Original`` in all cases.
122+
This is useful when you want to simplify complex type signatures.
123+
124+
In contrast, ``NewType`` declares one type to be a *subtype* of another.
125+
Doing ``Derived = NewType('Derived', Original)`` will make the static type
126+
checker treat ``Derived`` as a *subclass* of ``Original``, which means a
127+
value of type ``Original`` cannot be used in places where a value of type
128+
``Derived`` is expected. This is useful when you want to prevent logic
129+
errors with minimal runtime cost.
130+
36131
Callable
37132
--------
38133

0 commit comments

Comments
 (0)