I have two classes inheriting from the same parent P
:
from abc import ABCMeta, abstractmethod
class P(object):
__metaclass__ = ABCMeta
@abstractmethod
def foo(self):
pass
class C(P):
pass
class D(tuple, P):
pass
The only difference is that D
inherited from tuple
and P
while C
inherits from P
only.
Now this is the behavior: c = C()
got error, as expected:
TypeError: Can't instantiate abstract class C with abstract methods foo
but d = D()
works without error!
I can even call d.foo()
. How can I explain this behaviour?
Abstract methods are tested for in the
object.__new__
method; when you inherit fromtuple
, which has its own__new__
method,object.__new__
is not called and the test for abstract methods is not made.In other words, mixing abstract methods with any of the built-in immutable types will cause this problem.
The only solution that works is to do your own test in
__new__
and then only if you put your abstract class beforetuple
when mixing in the two bases in a subclass.