自省(introspection)指在运行时判断一个对象的类型
Python中一切都是对象,自省是Python的强项
通过自省可以知道一个对象的能力、状态
type()
返回对象类型
a = list()
print(type(a))
#
dir()
是自省的一个重要函数,返回列表,列出对象所拥有的属性和方法
a = list()
print(dir(a))
# ['__add__', '__class__', '__contains__', '__delattr__', '__delitem__', '__dir__',
# '__doc__', '__eq__', '__format__', '__ge__', '__getattribute__', '__getitem__',
# '__gt__', '__hash__', '__iadd__', '__imul__', '__init__', '__init_subclass__',
# '__iter__', '__le__', '__len__', '__lt__', '__mul__', '__ne__', '__new__',
# '__reduce__', '__reduce_ex__', '__repr__', '__reversed__', '__rmul__', '__setattr__',
# '__setitem__', '__sizeof__', '__str__', '__subclasshook__',
# 'append', 'clear', 'copy', 'count', 'extend', 'index', 'insert', 'pop', 'remove', 'reverse', 'sort']
直接用dir()
看上去非常杂乱,使用pdir()
可以美化输出
安装
pip install pdir2
代码
import pdir
a = list()
print(pdir(a))
Python标准库中的inspect模块用于获取对象的信息,主要的功能有:
查看该模块的函数及其含义:
import pdir
import inspect
print(pdir(inspect))
'''
property:
......
module attribute:
......
special attribute:
......
class:
......
function:
......
getmembers: Return all members of an object as (name, value) pairs sorted by name.
getdoc: Get the documentation string for an object.
getmodule: Return the module an object was defined in, or None if not found.
getfile: Work out which source or compiled file an object was defined in.
getsourcefile: Return the filename that can be used to locate an object's source.
getsource: Return the text of the source code for an object.
signature: Get a signature object for the passed callable.
getclasstree: Arrange the given list of classes into a hierarchy of nested lists.
getfullargspec: Get the names and default values of a callable object's parameters.
formatargspec: Format an argument spec from the values returned by getfullargspec.
getcallargs: Get the mapping of arguments to values.
getattr_static: Retrieve attributes without triggering dynamic lookup via the
......
exception:
EndOfBlock: Common base class for all non-exit exceptions.
'''
getmembers()
以键值对列表的形式返回对象所有成员信息
is开头的函数名可作为 getmembers()
的第2个参数
from inspect import *
a = [1, 2, 3]
print(getmembers(a))
print(getmembers(a, isclass)) # 返回类型
print(getmembers(a, isbuiltin)) # 返回内置函数
# [('__add__', ), ('__class__', ), ('__contains__', ), ('__delattr__', ), ('__delitem__', ), ('__dir__', ), ('__doc__', "list() -> new empty list\nlist(iterable) -> new list initialized from iterable's items"), ('__eq__', ), ('__format__', ), ('__ge__', ), ('__getattribute__', ), ('__getitem__', ), ('__gt__', ), ('__hash__', None), ('__iadd__', ), ('__imul__', ), ('__init__', ), ('__init_subclass__', ), ('__iter__', ), ('__le__', ), ('__len__', ), ('__lt__', ), ('__mul__', ), ('__ne__', ), ('__new__', ), ('__reduce__', ), ('__reduce_ex__', ), ('__repr__', ), ('__reversed__', ), ('__rmul__', ), ('__setattr__', ), ('__setitem__', ), ('__sizeof__', ), ('__str__', ), ('__subclasshook__', ), ('append', ), ('clear', ), ('copy', ), ('count', ), ('extend', ), ('index', ), ('insert', ), ('pop', ), ('remove', ), ('reverse', ), ('sort', )]
# [('__class__', )]
# [('__dir__', ), ('__format__', ), ('__getitem__', ), ('__init_subclass__', ), ('__new__', ), ('__reduce__', ), ('__reduce_ex__', ), ('__reversed__', ), ('__sizeof__', ), ('__subclasshook__', ), ('append', ), ('clear', ), ('copy', ), ('count', ), ('extend', ), ('index', ), ('insert', ), ('pop', ), ('remove', ), ('reverse', ), ('sort', )]
class T:
def f(self):
pass
print(getmembers(T(), isbuiltin))
print(getmembers(T(), isroutine)) # 返回内置函数,包括用户自定义
# [('__dir__', ), ('__format__', ), ('__init_subclass__', ), ('__new__', ), ('__reduce__', ), ('__reduce_ex__', ), ('__sizeof__', ), ('__subclasshook__', )]
# [('__dir__', ), ('__format__', ), ('__init_subclass__', ), ('__new__', ), ('__reduce__', ), ('__reduce_ex__', ), ('__sizeof__', ), ('__subclasshook__', ), ('f', >)]
getdoc()
:获取文档
getmodule()
:获取所属模块
getfile()
:获取定义对象的文件的名称
getsourcefile()
:获取定义对象的源文件
getsource()
:获取源代码
import requests
from inspect import *
from collections import defaultdict
a = [1, 2, 3]
print(getdoc(list)) # list初始化的文档
print(getdoc(list.append)) # list.append()的文档
# list() -> new empty list
# list(iterable) -> new list initialized from iterable's items
# L.append(object) -> None -- append object to end
print(getmodule(defaultdict)) # 所属模块
#
print(getfile(requests)) # 定义对象的文件的名称
print(getsourcefile(requests)) # 定义对象的源文件
# C:\Users\Administrator\AppData\Local\Programs\Python\Python36\lib\site-packages\requests\__init__.py
# C:\Users\Administrator\AppData\Local\Programs\Python\Python36\lib\site-packages\requests\__init__.py
def f():
print('Hello World!')
print(getsource(f)) # 源代码
# def f():
# print('Hello World!')
使用signature()
构建签名对象进行自省,获取参数列表
更多方法查阅inspect.Signature
from inspect import signature
def foo(a, *, b: int, **kwargs):
pass
sig = signature(foo)
print(sig) # 参数列表
print(sig.parameters['b']) # 参数b的类型
print(sig.parameters['b'].annotation) # 参数b的类型标注
# (a, *, b:int, **kwargs)
# b:int
#
getclasstree()
:返回类的继承关系
from inspect import *
from collections import OrderedDict
d = OrderedDict()
classes = getmembers(d, isclass) # 返回类型
print(classes)
classes = [cls[1] for cls in classes] # 组装
print(classes)
tree = getclasstree(classes) # 返回类的继承关系
print(tree)
# [('__class__', )]
# []
# [(, (,)), [(, (,))]]
getfullargspec()
:获取完整参数信息
from inspect import *
def f(a: int, b: float):
pass
print(formatargspec(*getfullargspec(f)))
# (a: int, b: float)
getcallargs()
:获取调用参数
from inspect import *
def f(a, b=1, *pos, **named):
pass
print(getcallargs(f, 1, 2, 3))
print(getcallargs(f, a=2, x=4))
try:
getcallargs(f)
except Exception as e:
print(e)
# {'a': 1, 'b': 2, 'pos': (3,), 'named': {}}
# {'pos': (), 'named': {'x': 4}, 'a': 2, 'b': 1}
# f() missing 1 required positional argument: 'a'
更多内容查阅解释器堆栈
from inspect import *
print(getframeinfo(currentframe()))
# Traceback(filename='D:/code/test/test.py', lineno=4, function='', code_context=['print(getframeinfo(currentframe()))\n'], index=0)
import math
from inspect import *
class T:
pi = 3.14
print(getattr_static(T, 'pi'))
print(getattr_static(math, 'pi'))
# 3.14
# 3.141592653589793