You signed in with another tab or window. Reload to refresh your session.You signed out in another tab or window. Reload to refresh your session.You switched accounts on another tab or window. Reload to refresh your session.Dismiss alert
Copy file name to clipboardExpand all lines: peps/pep-0718.rst
+69-3Lines changed: 69 additions & 3 deletions
Display the source diff
Display the rich diff
Original file line number
Diff line number
Diff line change
@@ -202,9 +202,75 @@ Interactions with ``@typing.overload``
202
202
^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
203
203
204
204
Overloaded functions should work much the same as already, since they have no effect on
205
-
the runtime type. The only change is that more situations will be decidable and the
206
-
behaviour/overload can be specified by the developer rather than leaving it to ordering
207
-
of overloads/unions.
205
+
the runtime type. This change will lead to more expressiveness with user's able to
206
+
decide and the behaviour/overload can be specified by the developer rather than leaving
207
+
it to ordering of overloads/unions.
208
+
209
+
.. code-block:: python
210
+
211
+
# N.B. `class bytes(Sequence[int]): ...` and `Foo` is a non-specified generic type
212
+
@overload
213
+
def seq_first[T: Sequence[int]](x: T) -> T: ...
214
+
@overload
215
+
def seq_first[T: bytes](x: T) -> Foo[T]: ...
216
+
217
+
@overload
218
+
def bytes_first[T: bytes](x: T) -> Foo[T]: ...
219
+
@overload
220
+
def bytes_first[T: Sequence[int]](x: T) -> T: ...
221
+
222
+
reveal_type(seq_first(b"")) # type is bytes
223
+
reveal_type(bytes_first(b"")) # type is Foo[bytes]
224
+
225
+
Explicit specialisation will restrict the set of available overloads
226
+
227
+
.. code-block:: python
228
+
229
+
@overload
230
+
def make[T](x: T) -> T: ...
231
+
@overload
232
+
defmake(x: str, y: str) -> tuple[int, int]: ...
233
+
234
+
reveal_type(make[int](1)) # type is int
235
+
reveal_type(make[int]("foo", "bar")) # Invalid: no overload for `make[int](x:str, y: str)` found, a similar overload exists but explicit specialisation prevented its use
236
+
237
+
Functions Parameterized by ``TypeVarTuple``s
238
+
^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
239
+
Currently type checkers disallow the use of multiple ``TypeVarTuple``s in it's generic
240
+
parameters, however it is currently valid to have a function as such
241
+
242
+
.. code-block:: python
243
+
244
+
def foo[*T, *U](bar: Bar[*T], baz: Baz[*U]): ...
245
+
def spam[*T](bar: Bar[*T]): ...
246
+
247
+
This PEP does not allow similar functions to be subscripted, for the same reason as
248
+
defined in :pep:`PEP 646<646#multiple-type-variable-tuples-not-allowed>`.
249
+
250
+
.. code-block:: python
251
+
252
+
foo[int, str, bool, complex](Bar(), Baz()) # Invalid: cannot determine which parameters are passed to *T and *U. Explicitly parameterise the instances individually
253
+
spam[int, str, bool, complex](Bar()) # OK
254
+
255
+
256
+
Binding Rules
257
+
^^^^^^^^^^^^^
258
+
Subscriptions on methods (including classmethods, staticmethods etc.) should only have
259
+
access to their function's type parameters and not the enclosing class's. Subscription
260
+
should follow the rules specified in :pep:`PEP 696<696#binding-rules>` methods should
261
+
be bound on attribute access.
262
+
263
+
.. code-block:: python
264
+
265
+
class C[T]:
266
+
def method[U](self, x: T, y: U): ...
267
+
@classmethod
268
+
def cls[U](cls, x: T, y: U): ...
269
+
270
+
C[int].method[str](0, "") # OK
271
+
C[int].cls[str](0, "") # OK
272
+
C.cls[int, str](0, "") # Invalid: too many type parameters
273
+
C.cls[str](0, "") # OK, T is ideally bound to int here though this is open for type checkers to decide
0 commit comments