Welcome to OGeek Q&A Community for programmer and developer-Open, Learning and Share
Welcome To Ask or Share your Answers For Others

Categories

0 votes
337 views
in Technique[技术] by (71.8m points)

python - __abstractmethods__ and AttributeError

I was playing with the dir() builtin function when I noticed this:

>>> dir(type)
['__abstractmethods__', '__base__', '__bases__', '__basicsize__', '__call__', '__class__', '__delattr__', '__dict__', '__dictoffset__', '__dir__', '__doc__', '__eq__', '__flags__', '__format__', '__ge__', '__getattribute__', '__gt__', '__hash__', '__init__', '__instancecheck__', '__itemsize__', '__le__', '__lt__', '__module__', '__mro__', '__name__', '__ne__', '__new__', '__prepare__', '__qualname__', '__reduce__', '__reduce_ex__', '__repr__', '__setattr__', '__sizeof__', '__str__', '__subclasscheck__', '__subclasses__', '__subclasshook__', '__text_signature__', '__weakrefoffset__', 'mro']
>>> type.__abstractmethods__
Traceback (most recent call last):
  File "<stdin>", line 1, in <module>
AttributeError: __abstractmethods__
>>> list.__abstractmethods__
Traceback (most recent call last):
  File "<stdin>", line 1, in <module>
AttributeError: __abstractmethods__

I don't understand, it appears in the list, why am I getting such error?

See Question&Answers more detail:os

与恶龙缠斗过久,自身亦成为恶龙;凝视深渊过久,深渊将回以凝视…
Welcome To Ask or Share your Answers For Others

1 Reply

0 votes
by (71.8m points)

__abstractmethods__ is a descriptor to support Abstract Base Classes; it wraps a slot that is empty by default (so the descriptor raises an attribute error). Most of all, it is an implementation detail of how CPython handles abstract methods.

The attribute is used to track what methods are abstract, so that instances can be blocked from being created if they don't provide concrete implementations:

>>> import abc
>>> class FooABC(metaclass=abc.ABCMeta):
...     @abc.abstractmethod
...     def bar(self):
...         pass
... 
>>> FooABC.__abstractmethods__
frozenset({'bar'})
>>> class Foo(FooABC): pass
... 
>>> Foo()
Traceback (most recent call last):
  File "<stdin>", line 1, in <module>
TypeError: Can't instantiate abstract class Foo with abstract methods bar

The abc.ABCMeta implementation sets the __abstractmethods__ attribute, and type() uses it to check for any abstract methods that should have been implemented but are not.


与恶龙缠斗过久,自身亦成为恶龙;凝视深渊过久,深渊将回以凝视…
OGeek|极客中国-欢迎来到极客的世界,一个免费开放的程序员编程交流平台!开放,进步,分享!让技术改变生活,让极客改变未来! Welcome to OGeek Q&A Community for programmer and developer-Open, Learning and Share
Click Here to Ask a Question

...