How to use __subclasshook__ with Mypy? #1127
-
How come that under Mypy, For instance, this program from collections.abc import Hashable
class A:
def __hash__(self) -> int:
return 0
a: Hashable = A() outputs
But this equivalent program from abc import ABCMeta, abstractmethod
def _check_methods(C: type, *methods: str) -> bool:
mro = C.__mro__
for method in methods:
for B in mro:
if method in B.__dict__:
if B.__dict__[method] is None:
return NotImplemented
break
else:
return NotImplemented
return True
class Hashable(metaclass=ABCMeta):
__slots__ = ()
@abstractmethod
def __hash__(self) -> int:
return 0
@classmethod
def __subclasshook__(cls, C: type) -> bool:
if cls is Hashable:
return _check_methods(C, "__hash__")
return NotImplemented
class A:
def __hash__(self) -> int:
return 0
a: Hashable = A() outputs
Does Mypy handle one-trick ponies in a special way? |
Beta Was this translation helpful? Give feedback.
Replies: 2 comments 5 replies
-
|
Beta Was this translation helpful? Give feedback.
-
It's important to recognise that mypy has no knowledge of the runtime implementations of anything in the standard library (this is because most of the standard library doesn't have type annotations). The same goes for most other static type checkers. For the standard library, all mypy knows about is the stubs that are provided for these classes in typeshed. You'll find the definition for |
Beta Was this translation helpful? Give feedback.
It's important to recognise that mypy has no knowledge of the runtime implementations of anything in the standard library (this is because most of the standard library doesn't have type annotations). The same goes for most other static type checkers.
For the standard library, all mypy knows about is the stubs that are provided for these classes in typeshed. You'll find the definition for
Hashable
in typeshed here, and you'll find that it's completely different to the implementation at runtime. This is why simply copying the runtime implementation produces code that mypy cannot understand — if you copy the implementation in typeshed instead, you should find that mypy is perfectly able to u…