问题
I've changed attributes for other classes before without issues. _Element is obviously not a built-in.
from lxml.etree import _Element
_Element.new_attr = 54
results in:
TypeError: can't set attributes of built-in/extension type 'lxml.etree._Element'
回答1:
_Element
is implemented in Cython. As Steve Holden explains (my emphasis),
The problem is that extension types' attributes are determined by the layout of the object's slots and forever fixed in the C code that implements them: the slots can't be extended, so there's no way to add attributes. This is an efficiency feature: it would be extremely slow to look up the basic types' attributes using late-binding (it would also change the nature of the language somewhat, making it more like Ruby or Self).
and Guido van Rossum explains why this is by-design:
This is prohibited intentionally to prevent accidental fatal changes to built-in types (fatal to parts of the code that you never though of). Also, it is done to prevent the changes to affect different interpreters residing in the address space, since built-in types (unlike user-defined classes) are shared between all such interpreters.
回答2:
The _Element
class is from a Cython compiled binary module. These are not Python 1st citizen objects and you cannot add arbitrary attributes to such objects.
来源:https://stackoverflow.com/questions/45773832/really-weird-cant-set-attributes-of-built-in-extension-type-lxml-etree-ele