首页 最新 热门 推荐

  • 首页
  • 最新
  • 热门
  • 推荐

Python语法学习记录(24):inspect模块介绍及常用使用方式

  • 25-03-03 18:20
  • 3669
  • 11044
blog.csdn.net

1、简述

获取函数签名对象。

函数签名包含了一个函数的信息,包括函数名、它的参数类型、它所在的类和名称空间及其他信息)。

2、基本用法

inspect模块主要提供了四种用处:

1.对是否是模块、框架、函数进行类型检查
2.获取源码
3.获取类或者函数的参数信息
4.解析堆栈

2.1 对是否是模块、框架、函数进行类型检查

inspect.getmembers

getmembers的实现步骤

获取 object 的所有成员的名字,包含 object 的父类的成员,存入 names 列表
从 object 的基类中获取 DynamicClassAttribute 类型的成员,添加到 names 列表中
遍历 names 列表,通过 getattr 方法获取 object 中所有属性的值,getattr(x, ‘y’) 相当于 x.y
用 predicate 判断成员值,把通过判断的成员,以(成员名, 成员值)的形式添加到 results 这个列表中
对 results 列表按 成员名 进行排序

inspect.getmembers(object[, predicate])
  • 1

第二个参数通常可以根据需要调用如下16个方法;

返回值为object的所有成员,以(name,value)对组成的列表

inspect.ismodule(object): 是否为模块
inspect.isclass(object):是否为类
inspect.ismethod(object):是否为方法(bound method written in python)
inspect.isfunction(object):是否为函数(python function, including lambda expression)
inspect.isgeneratorfunction(object):是否为python生成器函数
inspect.isgenerator(object):是否为生成器
inspect.istraceback(object): 是否为traceback
inspect.isframe(object):是否为frame
inspect.iscode(object):是否为code
inspect.isbuiltin(object):是否为built-in函数或built-in方法
inspect.isroutine(object):是否为用户自定义或者built-in函数或方法
inspect.isabstract(object):是否为抽象基类
inspect.ismethoddescriptor(object):是否为方法标识符
inspect.isdatadescriptor(object):是否为数字标识符,数字标识符有__get__ 和__set__属性; 通常也有__name__和__doc__属性
inspect.isgetsetdescriptor(object):是否为getset descriptor
inspect.ismemberdescriptor(object):是否为member descriptor
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • 9
  • 10
  • 11
  • 12
  • 13
  • 14
  • 15
  • 16

inspect的getmembers()方法可以获取对象(module、class、method等)的如下属性:

AttributeTypeDescriptionNotes
__doc__moduledocumentation string 文档字符串
__file__filename (missing for built-in modules) 文件名(内置模块没有文件名)
__doc__classdocumentation string 文档字符串
__module__name of module in which this class was defined 该类型被定义时所在的模块的名称
__doc__methoddocumentation string 文档字符串
__name__name with which this method was defined 该方法定义时所使用的名称
im_classclass object that asked for this method(1)
im_func or __func__function object containing implementation of method 实现该方法的函数对象
im_self or __self__instance to which this method is bound, or None 该方法被绑定的实例,若没有绑定则为 None
__doc__functiondocumentation string 文档字符串
__name__name with which this function was defined 用于定义此函数的名称
func_codecode object containing compiled function bytecode 包含已编译函数的代码对象
func_defaultstuple of any default values for arguments
func_doc(same as __doc__)
func_globalsglobal namespace in which this function was defined
func_name(same as __name__)
__iter__generatordefined to support iteration over container
closeraises new GeneratorExit exception inside the generator to terminate the iteration
gi_codecode object
gi_frameframe object or possibly None once the generator has been exhausted
gi_runningset to 1 when generator is executing, 0 otherwise
nextreturn the next item from the container
sendresumes the generator and “sends” a value that becomes the result of the current yield-expression
throwused to raise an exception inside the generator
tb_frametracebackframe object at this level 此级别的框架对象
tb_lastiindex of last attempted instruction in bytecode
tb_linenocurrent line number in Python source code
tb_nextnext inner traceback object (called by this level)
f_backframenext outer frame object (this frame’s caller)
f_builtinsbuiltins namespace seen by this frame
f_codecode object being executed in this frame
f_exc_tracebacktraceback if raised in this frame, or None
f_exc_typeexception type if raised in this frame, or None
f_exc_valueexception value if raised in this frame, or None
f_globalsglobal namespace seen by this frame
f_lastiindex of last attempted instruction in bytecode
f_linenocurrent line number in Python source code
f_localslocal namespace seen by this frame
f_restricted0 or 1 if frame is in restricted execution mode
f_tracetracing function for this frame, or None
co_argcountcodenumber of arguments (not including * or ** args)
co_codestring of raw compiled bytecode 原始编译字节码的字符串
co_conststuple of constants used in the bytecode 字节码中使用的常量元组
co_filenamename of file in which this code object was created 创建此代码对象的文件的名称
co_firstlinenonumber of first line in Python source code
co_flagsbitmap: 1=optimized | 2=newlocals | 4=*arg |8=**arg
co_lnotabencoded mapping of line numbers to bytecode indices 编码的行号到字节码索引的映射
co_namename with which this code object was defined 定义此代码对象的名称
co_namestuple of names of local variables 局部变量名称的元组
co_nlocalsnumber of local variables 局部变量的数量
co_stacksizevirtual machine stack space required 需要虚拟机堆栈空间
co_varnamestuple of names of arguments and local variables 参数名和局部变量的元组
__doc__builtindocumentation string 文档字符串
__name__original name of this function or method 此函数或方法的原始名称
__self__instance to which a method is bound, or None

例子:

import inspect
# 待获取签名的函数
def func(x:int, y:str, z:list) -> None:
    '''
    weiwei
    '''
    pass
# return signature类型的对象,值为函数的所有参数
print(inspect.signature(func))
# return orderdict key就是参数名  str类型
print(inspect.signature(func).parameters)
# return module的所有成员的name和obj类型
print(inspect.getmembers(func))
# 返回document
print(inspect.getdoc(func))

print(inspect.isfunction(func))         # 是否是函数 
print(inspect.ismethod(func))           # 是否是类的方法 
print(inspect.isgenerator(func))        # 是否是生成器对象 
print(inspect.isgeneratorfunction(func))# 是否是生成器函数 
print(inspect.isclass(func))            # 是否是类 
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • 9
  • 10
  • 11
  • 12
  • 13
  • 14
  • 15
  • 16
  • 17
  • 18
  • 19
  • 20
  • 21

2.2 获取源码

inspect.getdoc(object)# 获取object的documentation信息
inspect.getcomments(object)
inspect.getfile(object)# 返回对象的文件名
inspect.getmodule(object)# 返回object所属的模块名
inspect.getsourcefile(object)# 返回object的python源文件名;object不能使built-in的module, class, mothod
inspect.getsourcelines(object)# 返回object的python源文件代码的内容,行号+代码行
inspect.getsource(object)# 以string形式返回object的源代码
inspect.cleandoc(doc)
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8

2.3 获取类或者函数的参数信息

inspect.getclasstree(classes[, unique])
inspect.getargspec(func)
inspect.getargvalues(frame)
inspect.formatargspec(args[, varargs, varkw, defaults, formatarg, formatvarargs, formatvarkw, formatvalue, join])
inspect.formatargvalues(args[, varargs, varkw, locals, formatarg, formatvarargs, formatvarkw, formatvalue, join])
inspect.getmro(cls)#元组形式返回cls类的基类(包括cls类),以method resolution顺序;通常cls类为元素的第一个元素
inspect.getcallargs(func[, *args][, **kwds])#将args和kwds参数到绑定到为func的参数名;对bound方法,也绑定第一个参数(通常为self)到相应的实例;返回字典,对应参数名及其值;
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7

例子:

>>> from inspect import getcallargs
>>> def f(a, b=1, *pos, **named):
...     pass
>>> getcallargs(f, 1, 2, 3)
{'a': 1, 'named': {}, 'b': 2, 'pos': (3,)}
>>> getcallargs(f, a=2, x=4)
{'a': 2, 'named': {'x': 4}, 'b': 1, 'pos': ()}
>>> getcallargs(f)
Traceback (most recent call last):
...
TypeError: f() takes at least 1 argument (0 given)
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • 9
  • 10
  • 11

2.4 解析堆栈

inspect.getframeinfo(frame[, context])
inspect.getouterframes(frame[, context])
inspect.getinnerframes(traceback[, context])
inspect.currentframe()
inspect.stack([context])
inspect.trace([context])
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6

3、使用实例一:获取一些常用监控信息

Parameter对象:保存在元组中,是只读的 ; name,参数的名字 ; annotation,参数的注解,可能没有定义 ;default,参数的缺省值,可能没有定义 ;empty,特殊的类,用来标记default属性或者注释annotation属性的空值 ; kind,实参如何绑定到形参,就是形参的类型

import inspect
# 待获取签名的函数
def func(x:int, y:str, z:list) -> None:
  pass

# 获取签名对象,包括函数名,参数等
sig = inspect.signature(func) 
print(type(sig))
print(sig)
# 获取签名中的参数,返回有序字典
params = sig.parameters 
print(params)
# 通过循环并解构
for k, v in enumerate(params.items()):
  name, param = v
  print(param.annotation, param.kind, param.name)
# 获取签名中的返回值类型
ret = sig.return_annotation
print(ret)
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • 9
  • 10
  • 11
  • 12
  • 13
  • 14
  • 15
  • 16
  • 17
  • 18
  • 19

image-20201020103044988

4、使用实例二:修饰器检测示例

检查用户输入是否符合参数注解的要求?

思路:调用时,判断用户输入的实参是否符合要求,用户感觉上还是在调用原函数,对用户输入的数据和声明的类型进行对比,如果不符合,提示用户。

import datetime, time
import inspect
def check_str(func):
    def wrapper(*args, **kwargs):
        obj = inspect.signature(func)
        params = obj.parameters
        for k, v in enumerate(params.items()):
            name, param = v
            for i in args:
                if not isinstance(i, param.annotation):
                    print("{}: {} is not string".format(name, i))
                    raise TypeError
        ret = func(*args, **kwargs)
        return ret
    return wrapper

@check_str
def str_add(str1:str, str2:str):
    new_str = str1 + str2
    print(new_str)
str_add("3", "4")
str_add(3, 4)
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • 9
  • 10
  • 11
  • 12
  • 13
  • 14
  • 15
  • 16
  • 17
  • 18
  • 19
  • 20
  • 21
  • 22

5、实例三:常用代码模块

5.1 获取该模块的所有类

import inspect

for name, obj in inspect.getmembers(unittest):
    """获取该模块的所有类"""
    if inspect.isclass(obj):
        print(obj.__name__)
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6

举例:

import inspect

for name, obj in inspect.getmembers(inspect):
 """获取该模块的所有类"""
 if inspect.isclass(obj):
     print(obj.__name__)
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6

5.2 获取某个类中的函数

举例

import inspect

class classtest():
 def __init__(self):
     '''哈哈哈'''
     a = 100
 def add(self):
     '''加法'''
     return self.a + 100

"""下面可以写出带序号的方法"""
driver = []
print(classtest.__init__.__doc__)
for i in inspect.getmembers(classtest):#获取Page类中的所有成员方法,i返回的是一个元祖,第一个元素是方法名,第二个是内存地址
 if inspect.isfunction(i[1]):#判断成员是不是一个函数方法
     driver.append(i[1].__doc__)#是打印他的doc
for i in enumerate(driver):
 print(i)
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • 9
  • 10
  • 11
  • 12
  • 13
  • 14
  • 15
  • 16
  • 17
  • 18

image-20201020160838364

Last

Python函数参数注释 - 阅读

python标准库中inspect 模块简单介绍_阿常呓语的专栏-CSDN博客

Python Inspect模块 - 知乎

python inspect.getmembers 源码分析

python–inspect模块-阿里云开发者社区

文章知识点与官方知识档案匹配,可进一步学习相关知识
Python入门技能树首页概览416632 人正在系统学习中
注:本文转载自blog.csdn.net的呆呆象呆呆的文章"https://blog.csdn.net/qq_41554005/article/details/109278882"。版权归原作者所有,此博客不拥有其著作权,亦不承担相应法律责任。如有侵权,请联系我们删除。
复制链接
复制链接
相关推荐
发表评论
登录后才能发表评论和回复 注册

/ 登录

评论记录:

未查询到任何数据!
回复评论:

分类栏目

后端 (14832) 前端 (14280) 移动开发 (3760) 编程语言 (3851) Java (3904) Python (3298) 人工智能 (10119) AIGC (2810) 大数据 (3499) 数据库 (3945) 数据结构与算法 (3757) 音视频 (2669) 云原生 (3145) 云平台 (2965) 前沿技术 (2993) 开源 (2160) 小程序 (2860) 运维 (2533) 服务器 (2698) 操作系统 (2325) 硬件开发 (2491) 嵌入式 (2955) 微软技术 (2769) 软件工程 (2056) 测试 (2865) 网络空间安全 (2948) 网络与通信 (2797) 用户体验设计 (2592) 学习和成长 (2593) 搜索 (2744) 开发工具 (7108) 游戏 (2829) HarmonyOS (2935) 区块链 (2782) 数学 (3112) 3C硬件 (2759) 资讯 (2909) Android (4709) iOS (1850) 代码人生 (3043) 阅读 (2841)

热门文章

101
推荐
关于我们 隐私政策 免责声明 联系我们
Copyright © 2020-2025 蚁人论坛 (iYenn.com) All Rights Reserved.
Scroll to Top