关于python:如何列出一个类的所有字段(没有方法)?

How to list all fields of a class (and no methods)?

假设o是一个python对象,我想要o的所有字段,而不需要任何方法或__stuff__。怎么能做到?

我试过这样的方法:

1
2
3
[f for f in dir(o) if not callable(f)]

[f for f in dir(o) if not inspect.ismethod(f)]

但是这些返回与dir(o)相同,可能是因为dir给出了字符串列表。另外,像__class__这样的东西会被退回这里,即使我能让它工作。


您可以通过__dict__属性或内置的vars函数获得它,这只是一个快捷方式:

1
2
3
4
5
6
7
8
9
10
11
12
13
>>> class A(object):
...     foobar = 42
...     def __init__(self):
...         self.foo = 'baz'
...         self.bar = 3
...     def method(self, arg):
...         return True
...
>>> a = A()
>>> a.__dict__
{'foo': 'baz', 'bar': 3}
>>> vars(a)
{'foo': 'baz', 'bar': 3}

对象只有属性。方法和类属性不存在。


基本答案是"你不能这么可靠地做"。看看这个问题。

你可以用[attr for attr in dir(obj) if attr[:2] + attr[-2:] != '____' and not callable(getattr(obj,attr))]得到近似值。

但是,您不应该依赖于此,因为:

Because dir() is supplied primarily as a convenience for use at an interactive prompt, it tries to supply an interesting set of names more than it tries to supply a rigorously or consistently defined set of names, and its detailed behavior may change across releases.

换句话说,没有规范的方法来获取"对象的所有属性"(或"对象的所有方法")的列表。

如果您正在进行某种动态编程,需要对对象的未知字段进行迭代,那么唯一可靠的方法就是实现自己的跟踪这些字段的方法。例如,您可以使用一个属性命名约定,或者一个特殊的"字段"对象,或者最简单的说,一个字典。


您可以迭代实例的s__dict__属性并查找非方法的内容。例如:

1
2
3
4
CALLABLES = (types.FunctionType, types.MethodType)
for key, value in A().__dict__.items():
    if not isinstance(value, CALLABLES):
        print key

输出:

1
2
foo
bar

您可以在一个单句中完成,并理解列表:

1
2
print [key for key, value in A.__dict__.items()
            if not isinstance(value, CALLABLES)]

将打印['foo', 'bar']


您可以使用内置方法vars()


这对可调用文件有效:

1
[f for f in dir(o) if not callable(getattr(o,f))]

你可以通过以下方式摆脱其余的:

1
[f for f in dir(o) if not callable(getattr(o,f)) and not f.startswith('__')]