Python 获取当前类的名称?

Python 获取当前类的名称?,python,class,Python,Class,如何获取我当前所在的类的名称 例如: def get_input(class_name): [do things] return class_name_result class foo(): input = get_input([class name goes here]) 由于我正在与之交互的程序(vistrails)的性质,我无法使用\uuu init\uuu()在类主体内初始化输入,类名尚未定义,因此不可用。您不能简单地键入类的名称吗?也许你需要对这个问题多说一

如何获取我当前所在的类的名称

例如:

def get_input(class_name):
    [do things]
    return class_name_result

class foo():
    input = get_input([class name goes here])

由于我正在与之交互的程序(vistrails)的性质,我无法使用
\uuu init\uuu()
在类主体内初始化
输入
,类名尚未定义,因此不可用。您不能简单地键入类的名称吗?也许你需要对这个问题多说一些,这样我们才能为你找到解决办法

我将创建一个元类来为您完成这项工作。它在类创建时被调用(概念上是在类的末尾:block),并且可以操作正在创建的类。我还没有测试过这个:

class InputAssigningMetaclass(type):
    def __new__(cls, name, bases, attrs):
        cls.input = get_input(name)
        return super(MyType, cls).__new__(cls, name, bases, newattrs)

class MyBaseFoo(object):
    __metaclass__ = InputAssigningMetaclass

class foo(MyBaseFoo):
    # etc, no need to create 'input'

class foo2(MyBaseFoo):
    # etc, no need to create 'input'

您可以通过类的私有属性访问它:

cls_name = self.__class__.__name__
编辑:


正如Ned Batcheler所说,这在类主体中不起作用,但在方法中起作用。

obj.\uuuuu class.\uuuu name.\uuuuu.\uuuuu
将获得任何对象名称,因此您可以执行以下操作:

class Clazz():
    def getName(self):
        return self.__class__.__name__
用法:

>>> c = Clazz()
>>> c.getName()
'Clazz'

编辑:是的,您可以;但是您必须作弊:当前运行的类名存在于调用堆栈上,并且模块允许您访问堆栈

>>> import traceback
>>> def get_input(class_name):
...     return class_name.encode('rot13')
... 
>>> class foo(object):
...      _name = traceback.extract_stack()[-1][2]
...     input = get_input(_name)
... 
>>> 
>>> foo.input
'sbb'
然而,我不会这样做;我最初的答案仍然是我自己喜欢的解决方案。原始答复:

可能最简单的解决方案是使用装饰器,这与Ned关于元类的回答类似,但功能较弱(装饰器可以使用黑魔法,但元类可以使用古老的神秘黑魔法)


我觉得应该是这样的,

    class foo():
        input = get_input(__qualname__)
介绍了在Python3.3中实现的
\uuuuqalName\uuuqalName

对于顶级函数和类,
\uuuu qualname\uuu
属性等于
\uu name\uuuu
属性。对于嵌套的类、方法和嵌套函数,
\uuuu qualname\uu
属性包含从模块顶层指向对象的点路径

它可以从类或函数的定义中访问,例如:

class Foo:
    print(__qualname__)
将有效打印
Foo
。 您将获得完全限定名(不包括模块名),因此您可能希望在
字符上拆分它

但是,无法获得所定义类的实际句柄

>>> class Foo:
...     print('Foo' in globals())
... 
False

@Yuval Adam回答使用@property

class Foo():
    @property
    def name(self):
        return self.__class__.__name__

f = Foo()
f.name  # will give 'Foo'


为了阐明我试图做什么:我需要在方法之外创建并初始化一个类变量“input”。我有一堆小类,每个类都必须使用它们的类名作为参数来调用“get_input”。我正在尝试概括这一点,这样我就不必去每一个类(大约有100个)并键入类的名称。好的,我已经用一个元类更新了我的答案,应该会有所帮助。在
InputAssigningMetaclass
中的
super
行中的
MyType
指的是什么?为什么这不是公认的答案?编辑:Ok OP的作用域不是内部的,它在类级别。@KomodoDave,因为这是错误的,即使在方法作用域中也是如此。当您从子类调用
getName
时,它将输出子类名称。如果您真的想要使用您正在使用的类,那么它会变得很棘手。@KenetJervet您的意思是当您从父类调用
getName
时,它会输出子类名称吗?好的,我要指出这一点。用面向对象的术语来说,解决方案(返回实际的运行时子类名,即使
getName()
方法恰好是在超类中定义的)是正确的。这现在是最好的答案!
>>> class Foo:
...     print('Foo' in globals())
... 
False
class Foo():
    @property
    def name(self):
        return self.__class__.__name__

f = Foo()
f.name  # will give 'Foo'