这里是清安,反射前面我们已经学过了,那么为什么还要写这一篇呢,因为__getattribute__这个属性拦截器,但是在某些情况下使用起来,对应的意义不一样。除了属性拦截器之外,它也能跟反射达到类似的效果,至于它的称呼,也有称之为反射。直接上实例吧:
_ _ getattr_ _
class Name(object): def __init__(self, name, text, info): self.name = name self.text = text self.info = info """查找不到属性的时候调用""" def __getattr__(self, item): return self.info['text'] if __name__ == '__main__': n = Name('QA', '你好', info={"text": '找不到啦'}) print(n.text) print(n.ddd)
首先我们看到__getattr__,看到代码中的文字描述了。这里就不多阐述了。
_ _ getattribute_ _
class Name(object): def __init__(self, name, text, info): self.name = name self.text = text self.info = info """查找不到属性的时候调用""" def __getattr__(self, item): return self.info['text'] def __getattribute__(self, item): return '你好啊,清安' if __name__ == '__main__': n = Name('QA', '你好', info={"text": '找不到啦'}) print(n.text) print(n.ddd)
接上一个例子,我们这直接新增一个方法进去,此处会发生什么呢?他为什么会被叫做属性拦截器?运行看看结果:
你好啊,清安 你好啊,清安
可以看到,并没有返回我们所想象的内容,例如说打印的结果是你好,找不到啦等。而是直接返回了__getattribute__的返回值。我们调用属性的时候,都被直接拦截了,可以理解为,__getattribute__的优先级最高,不论你调用那个属性,优先进入__getattribute__被执行。好了,上述两个例子可能并不是你想要了解的内容。那么我们结合selenium来跑一跑。这里运用了部分的POM思想来写,首先写一个简单的底层PY:
# -->>>清安<<<--- from selenium import webdriver from time import sleep class Test(object): def __init__(self): self.fox = webdriver.Firefox() self.fox.get('https://d2.shopxo.vip/') def get_element(self, *local): return self.fox.find_element(*local) def get_text(self, *local): sleep(1) txt = self.get_element(*local) print(txt.text)
此处命名随意。符合规则就好,然后我们再来看看另一个文件,命令随意,符合规则就行。
getattr
from class_getattr import Test from selenium.webdriver.common.by import By t = Test() getattr(t, 'get_text')(By.XPATH, '//div[@class="menu-hd"]')
先来看看反射getattr,反射在前面的内容中我们讲到过具体的用法,可以节省很多的代码量,此处就不做多的阐述了。这就是比较简单的一种传值用法。既然是传值,那么我们是不是可以用变量进行替代呢?用变量替代能完成什么事情,为什么要在selenium里面说。selenium写起来比较的麻烦,所以,此处我们以简单的例子,说明原理,用法。介绍思想,直接用于难得项目中实践即可。
重点:
用变量代替实际得值,我们可以反复的利用。可以写一个方法,比如说:
from class_getattr import Test from selenium.webdriver.common.by import By t = Test() def attr_(fun,location,ele) getattr(t, fun)(location, ele)
这样我们可以实现一个关键字传参的这么一个过程。至于如何实现,是在py文件里面写,还是用excel还是yaml亦或者其他的文件,那就看个人了。
_ _ getattribute_ _
上面我们已经见过这个了,属性拦截器,那么这里为什么又要讲它。因为它可以跟getattr近乎类似。
from class_getattr import Test from selenium.webdriver.common.by import By t = Test() t.__getattribute__('get_text')(By.XPATH, '//div[@class="menu-hd"]')
看上述的例子瞬间秒懂了吧,只是传值的方式不一样,实际实现的效果,依然可以获取到text文本值。
总结
getattr是Python的内置函数之一,它的作用是获取对象的属性。object.__getattribute__是一个对象方法,当访问某个对象的属性时,会无条件的调用这个方法。该方法应该返回属性值或者抛出AttributeError异常。而具体的实例上面已经介绍了,自己可以用在代码中试一试。而属性拦截器__getattribute__,在类中的使用的时候优先级也是最高的,这个方法用的好则是神器,用不好就是累赘。慎用。