Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

bpo-43224: Forbid TypeVar substitution with Unpack #32031

Merged

Conversation

serhiy-storchaka
Copy link
Member

@serhiy-storchaka serhiy-storchaka commented Mar 21, 2022

for A in G, Tuple:
B = A[T, Unpack[Ts], str, T2]
with self.assertRaises(TypeError):
B[int, Unpack[Ts]]
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Remind me where PEP 646 forbids this? Assuming Unpack[Ts] === *Ts, it seems this is forbidding the following:

class G(Generic[*Ts]): ...
B = G[T, *Ts, str, T2]
X = B[int, *Ts]  # <-- TypeError here

What is wrong with X that isn't wrong with B?

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I'll rewrite it as B[int, *Ts2], so we could unambiguously refer to variables.

AFAIK PEP 646 does not cover such case. It does not specify the result.

But what can be the result of substitution B[int, *Ts2]? T is substituted with int, T2 should be substituted with the last item of *Ts2, and *T should be substituted with all but the last items of *Ts2. But we cannot express this, because Ts2 is a variable. If we substitute *Ts2 with an empty sequence of types (X[()]), there would not be a value for T2.

I think that it is better to make it an error:

def f(a: tuple[*Ts2]) -> B[int, *Ts2]: ...

You should write

def f(a: tuple[*Ts2, T3]) -> B[int, *Ts2, T3]: ...

to make it having some sense.

There is a workaround of this problem. It may even make the code more clear. You can see, that a should be a tuple containing at least 1 item. T2 in B will be substituted with the type of the last item, and *Ts in B will be substituted with the rest of types.

Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

@mrahtz what do you think of this case?

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Thanks for the prod, Jelle. I agree with Serhiy - looks like this is one of the cases we should forbid at runtime.

Copy link
Member

@JelleZijlstra JelleZijlstra left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Looks good in principle, pending resolution of Guido's question.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
skip news type-feature A feature request or enhancement
Projects
None yet
Development

Successfully merging this pull request may close these issues.

6 participants