python_day7_反射

Posted

tags:

篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了python_day7_反射相关的知识,希望对你有一定的参考价值。

反射:

    1、内置函数 hasattr,getattr,setattr,delattr

    2、动态导入模块

    3、__setattr__,__delattr__,__getattr__


# 理论知识来源:http://www.cnblogs.com/linhaifeng/articles/6204014.html#_label2


1、反射:

    python面向对象中的反射:通过字符串的形式操作对象相关的属性。python中的一切事物都是对象(都可以使用反射)

    四个可以实现自省的函数

    下列方法适用于类和对象(一切皆对象,类本身也是一个对象)

    

    # ------------- 演示类 -------------

class te1:
def __init__(self,name,addr):
    self.name = name
    self.addr = addr    

t1=te1('xiong','bj')
print(t1.__dict__)      # {'name': 'xiong', 'addr': 'bj'}

        #-----------------------------------


hasattr:    #bool值  false,true
# 使用格式: hasattr(实例,'str')  相等于直接调用了t1.name存在就true否则就false
print(hasattr(t1,'name'))   # True
print(hasattr(t1,'22'))     # False

getattr:    # 没有值就会报错
# 使用格式 getattr(class,'str',返回内容)    # 直接获取结果 相等于print(t1.name)
print(getattr(t1,'name'))      # xiong
print(getattr(t1,'nam11e'))     # 当值不存在时,AttributeError: 'te1' object has no attribute 'nam11e'
print(getattr(t1,'nam11e','不存在'))   # 如果有返回值,那么它就直接返回   "不存在"

setattr     # 相等于实例.key=值
# 使用格式 setattr(class,'str','值')
setattr(t1,'xiong','123')       # 相等于 t1.xiong='123'
print(t1.__dict__)              # {'name': 'xiong', 'addr': 'bj', 'xiong': '123'}

# delattr   # 相等于  del 实例.key
# 使用格式 delattr(class,'key')  
delattr(t1,'xiong')       # 相等于 del t1.xiong
print(t1.__dict__)      # 打印结果: {'name': 'xiong', 'addr': 'bj'}

    # 使用反射的好处:

        # 可以事先定义好接口,接口只有在被完成后才会真正执行,这实现了即插即用,这其实是一种‘后期绑定’,什么意思?即你可以事先把主要的逻辑写好(只定义接口),然后后期再去实现接口的功能


2、动态导入模块

    # ------------- 一般正常导入模块

        # m1是目录 f1是一个.py文件,里头定义了一个 test函数

from m1 import f1
f1.test()   # 直接返回结果 test

# --------- 使用字符串导入模块
m=__import__('m1.f1')
print(m)        # <module 'm1' (namespace)>  # 导入之后不管多少层目录,调用它只能从第一层.t.x.x使用

# 如 m.f1.test()   打印结果: test

# 调用方式二
    m1=importlib.import_module('m1.f1')
    print(m1)       # 打印结果:<module 'm1.f1' from 'C:\\Users\\xiong\\Desktop\\py2\\基础版_day4_对象\\m1\\f1.py'>

# 使用importlib函数的话那么导入完之后它就会在模块那层, 直接使用函数就能返回
# m1.test()    # 打印结果:test


3、类内置方法

class te1:
    def __init__(self,name,addr):
        self.name = name
        self.addr = addr    

    def __getattr__(self, item):
        return '__getattr__运行'

    def __setattr__(self, key, value):
        print('__setattr__运行')
        # self.key = value      # RecursionError: maximum recursion depth exceeded
        self.__dict__[key]=value  # 应当使用它

    def __delattr__(self, item):
        print('__delattr__执行')
        self.__dict__.pop(item)    # 应当使用它直接在类中的字典中操作删除健值对

t1=te1('ge','j')
print(t1.namef)         # 没有这个属性,为false时才会返回__getattr__结果

t1=te1('ade','j')        # 执行self.key = value时会报 RecursionError: maximum recursion depth exceeded错误
t1.x=1
print(t1.__dict__)      # {'name': 'ge', 'addr': 'j', 'x': 1} 会增加一个健值对

del t1.addr             # 执行 __delattr__类内置方法 使用字典pop删除的方式
print(t1.__dict__)      # __delattr__执行 {'name': 'ge', 'x': 1}

以上是关于python_day7_反射的主要内容,如果未能解决你的问题,请参考以下文章

Python_Day7_面向对象学习

python_day7学习笔记

Python_Day8_面向对象编程进阶

Python_day02_2018.7.3

python_day9_socket

python_day9_socket