我在python docs中看到了以下内容:
BOOL([X])
使用标准真值测试程序将值转换为布尔值。如果x为false或省略,则返回False;否则它 返回True。 bool也是一个类,它是int的子类。的类 bool不能进一步子类化。它的唯一实例是False和 真。
我生命中从未希望将bool
作为子类,但我自然而然地立即尝试了它,果然:
>>> class Bool(bool):
pass
Traceback (most recent call last):
File "<pyshell#2>", line 1, in <module>
class Bool(bool):
TypeError: Error when calling the metaclass bases
type 'bool' is not an acceptable base type
所以,问题是:这是怎么做到的?我是否可以应用相同的技术(或不同的技术)将我自己的类标记为final
,即为了防止它们被子类化?
答案 0 :(得分:14)
bool
类型在C中定义,其tp_flags
广告位故意不包含Py_TPFLAGS_BASETYPE
flag。
C类型需要将自己显式标记为可子类化。
要为自定义Python类执行此操作,请使用元类:
class Final(type):
def __new__(cls, name, bases, classdict):
for b in bases:
if isinstance(b, Final):
raise TypeError("type '{0}' is not an acceptable base type".format(b.__name__))
return type.__new__(cls, name, bases, dict(classdict))
class Foo:
__metaclass__ = Final
class Bar(Foo):
pass
给出:
>>> class Bar(Foo):
... pass
...
Traceback (most recent call last):
File "<stdin>", line 1, in <module>
File "<stdin>", line 5, in __new__
TypeError: type 'Foo' is not an acceptable base type