Closed decorator-factory closed 3 years ago
One issue, though: Mapping
expects the key type to be invariant and the value type to be covariant.
Not only that, but Map[K, V]
's key and value type are covariant, because it's equivalent to tuple[tuple[K, V], ...]
or frozenset[tuple[K, V]]
.
I'm not sure how this should be approached.
However, with
Map
, this is fine, it just produces a map of different type:
I don't think this is a good idea. Map.update()
is semantically equivalent to dict
mutation and the original type constraint is still valuable in most cases to prevent erroneous use. This change effectively makes Map
to behave as if it was Any
in the key for all mutations.
One issue, though:
Mapping
expects the key type to be invariant and the value type to be covariant. Not only that, butMap[K, V]
's key and value type are covariant [...] I'm not sure how this should be approached.
This is exactly why Mapping
is invariant in key: it's the only way to soundly satisfy key contravariance in __getitem__
and its covariance in various key-returning methods (keys()
, values()
).
@elprans Am I understanding you correct that Map
should be invariant in key and covariant in value?
Am I understanding you correct that
Map
should be invariant in key and covariant in value?
That's right.
@elprans After playing around with this locally, I think the types need to be updated a bit more substantially than this PR addresses. I'll be submitting a new PR soon to address what I've found.
@bryanforbes @elprans Thanks for the review. I guess this PR is made obsolete by #62, so I can close it?
I think restricting the type of update
is a good idea (because it will prevent likely mistakes and not cause long and confusing error messages), and if someone wants unionized updates, they can make a separate function with the required signature.
This PR aims to do three things:
Make use of type annotations Before, only
_map
was annotated, so the type checker (Pylance in my case) wasn't picking up on it. This is done usingTYPE_CHECKING
, which is available since Python 3.5.2.Additional constraints when using
**kwargs
: Specifically, this is wrong:so if
**kwargs
are used, the key type should be a subtype ofstr
Allowing more valid updates With
dict
or any other mutable mapping, this is wrong:However, with
Map
, this is fine, it just produces a map of different type: