Python 3.7:
我有一个类定义,其中class属性根据类名分配一个值,该值用于类中的装饰器。
我正在寻找“正在定义的班级”的代名词。
这是一个例子:
class MyClass:
# NameError: name '__class__' is not defined
class_logger = find_logger(__class__.__name__)
# __init__ is not important
def __init__(self):
# This works!
self.logger = find_logger(__class__.__name__)
@mydecorator(class_logger)
# mymethod is not important
def mymethod(self):
return 1
什么是“正在定义的班级”的合适代名词?
(这类似于How to get the current Python class name in __init__ regardless of the class of "self"?,但在那里,问题是“在init的定义中”,当时是2.7。Python 3.x解决了这个问题。)
当类定义尚未完成评估时,无法保证类对象存在且可供用户访问。即使它是可访问的,也可能没有初始化到你可以对它做任何有用的事情。
也就是说,您可以获得该课程的名称。 __qualname__
是一个属性,它包含类/函数/方法/描述符/生成器实例的qualified name。您应该能够从类的定义中访问它。
class Fred:
print("Fred's qualname:", __qualname__)
class Barney:
print("Barney's qualname:", __qualname__)
结果:
Fred's qualname: Fred
Barney's qualname: Fred.Barney
如果未在文件级定义类,则可能需要执行一些字符串操作以将其名称与路径的其余部分分开。例如,将上面的示例更改为print("Barney's qualname:", __qualname__.rpartition(".")[-1])
以获得“Barney”而不是“Fred.Barney”。
尽管我付出了最大的努力,但我找不到明确证实__qualname__
作为常规名称而不是作为属性访问时具有合理价值的文档。我并不完全相信这是明确定义的行为,因此我认为我无法毫无保留地认可它以获得生产质量的代码。
要在定义期间使用类名,您还可以使用带有__prepare__
方法的元类:
def find_logger(name):
return name + '_logger'
class PrepareClassLogger(type):
def __prepare__(name, bases, **kwargs):
return {'class_logger': find_logger(name)}
class MyClass(metaclass=PrepareClassLogger):
pass
print(MyClass.class_logger) # MyClass_logger