一. 什么是反射? 反射: 用字符串数据类型的变量名来访问这个变量的值 反射的方法: getattr,hasattr,setattr,delattr 反射可以用在: " 类, 对象, 模块, 反射自己模块中的内容" hasattr(判断要么是True, 要么是False), getattr # 根据字符串的形式,去对象中找成员。 hasattr # 根据字符串的形式,去判断对象中是否有成员。 类名.名字 相当于: getattr(类名, "名字") 对象名.名字 hasattr(对象, "名字") 模块名.名字 相当于: import 模块 getattr(模块, "名字") 自己文件.名字 相当于: import sys getattr(sys.modules["__main__"], "名字") == > 名字 修改 setattr(对象, 名字, 修改内容) 删除 delattr(对象, 名字)1. getattr和hasattr的用法
class Reflex(object):
reflex = '反射'
def __init__(self,name):
self.name = name
def func(self):
print('start func')
@classmethod
def login(cls):
print('登录')
r = Reflex('电视')
# getattr反射查看属性
print(r.reflex)
print(r.name)
print(getattr(r,'reflex'))
print(getattr(Reflex,'reflex'))
print(getattr(r,'name'))
# getattr反射调用方法
getattr(Reflex,'func')(1) # 反射要加括号,括号要传值,因为通过类经过反射调用的方法
getattr(Reflex,'login')() # 因为是类方法,不需要对象,所以对象不需要传值
# hasattr判断是否有这个, 属性/方法
num = input(">>>")
if hasattr(Reflex,num): # 判断是否有这个, 属性/方法
getattr(Reflex,num)(1) # 执行这个有这个方法
print(getattr(Reflex,num)) # 执行这个有这个属性
else:
print('没有你输入的这个方法或者属性')
2. 修改文件名
import os
os.rename("__init__.py","init") # 改变文件名字
getattr(os,"rename")("init","__init__.py") # 把 文件 init 变成 __init__.py 文件
print(getattr(os,"rename"))
# 内置函数
rename = os.rename # 赋值给rename
rename2 = getattr(os,"rename") # 赋值给rename2
rename("__init__.py","init")
rename2("init","__init__.py")
# 补充
# os模块和shutil的比较
import os
import shutil # 可以修改文件夹和文件名
# os在py2 + win中报错
os.rename('a.tst','b.tst')
# shutil在py2 和 py3都可以用
# 修改文件名
shutil.move('a.tst','b.tst')
# 可以删除文件夹
shutil.rmtree(r'D:\...\...\...')
3. sys.modules["__main__"]相当于把本文件当作一个模块去执行
import sys
# sys.modules["__main__"] == 当前模块
def func():
print("in func")
def func2():
print("in func2")
# 反射自己模块中的内容 找到自己当前文件所在的命名空间
modules = sys.modules['__main__'] # 当前模块,相当于把这个文件当做模块
modules.func()
modules.func2()
getattr(sys.modules['__main__'],'func')() # 反射
getattr(sys.modules['__main__'],'func2')()
print(sys.modules["__main__"]) # 拿到内存地址
# import 都相当于导入一个模块
# 模块那个导入了, 那个没导入 在我的python解释器里应该记录下来.
# import sys 是一个模块, 这个模块里的所有的方法都是和python解释器相关的
print(sys.modules) # '__main__': <module '__main__' from ......>
4. setattr和delattr的用法
class Reflex(object):
reflex = '反射'
def __init__(self,name):
self.name = name
def func(self):
print('start func')
@classmethod
def login(cls):
print('登录')
r = Reflex('电视')
# setattr修改,反射
setattr(Reflex,'reflex','不反射')
print(getattr(Reflex,'reflex'))
setattr(r,'name','电影')
print(getattr(r,'name'))
# delattr删除,反射
delattr(Reflex,'reflex')
# print(getattr(Reflex,'reflex')) # 报错