Pyhton——面向对象进阶二:
一、类的内置函数补充
1、isinstance(obj,cls)——检查obj是否是该类的对象
class Hoo:
def __init__(self,name,tem):
self.name = name
self.tem = tem
class foo(Hoo):
pass
f1=foo('e',20)
print(isinstance(f1,Hoo))
首先 f1 肯定是 foo 的对象,如果 Hoo 是 foo 的父类,那么 f1 也同样是 Hoo 的对象。
2、issubclass(sub,super)——检查sub类是否是super类的派生类(子类)
3、__getattribute __
首先 __getattribute __ 与前面的 __getattr __ 很像,当然他们实际的功能也类似:
可以看到,当执行不存在的方法时,应该是执行 __getattr __ 的,但是现在执行的却是 __getattribute __ ;接着我们看下,如果执行的是存在的方法呢?
可以看到,当执行的方法是存在的时候,依然执行的是 __getattribute __ 。所以,无论执行的方法存不存在,都会执行 __getattribute __ 。
那么这个方法有什么作用呢?跟__getattr __ 又有什么联系呢?首先先来看下,当执行一个不存在的方法时,其报错的异常
这是原本的异常。
在__getattribute __方法中,可以通过 raise AttributeError 来发出你想要发出的异常
如果此时 __getattribute __ 与 __getattr __ 同时存在会发生什么呢?
从以上结果可以看到,当这两个方法同时存在,且执行类里面没有的方法时,是不会发出异常的,本该出现的异常被 __getattr __接去了,
4、__setitem __ 、__getitem __ 与 __delitem __
这三个与前面的 attr 函数很类似,功能也差不多。直接上结论。
attr 函数主要是通过 点 的方式触发,当通过 点 来调用方法时,就会触发 attr 函数。而 item 函数主要是通过字典来触发,当用字典来操作的时候,就会触发 item 函数
从上面的结果可以印证上面的结论
如果要完成本来的功能,看下:
def __setitem__(self, key, value):
self.__dict__[key] = value
def __getitem__(self, item):
return self.__dict__[item]
def __delitem__(self, key):
self.__dict__.pop(key)
5(1)、__str __ ——打印显示方式
f1 是类的实例化对象,直接打印这个对象,会显示这么一串东西。如果我们想要显示别的行不行?
修改此 str 就可以显示自己要显示的东西
5(2)、__repr __ ——打印显示方式
可以看到这里 repr 也能显示自定义打印方式
同样是打印显示方式,str 与 repr 有什么区别呢?
repr 主要在解释器中触发
那么 repr 与 str 同时存在会打印哪个?
两个同时存在的情况下,调用的是 str ,但并不是优先执行谁,而是 print 本质调用的是 str方法,如果 找不到 str ,就会去找 repr 这个替代品
注意:str 与 repr 返回值必须是字符串,否则会抛出异常
6、自定制 format 方法
方法:略
主要通过运用字典的方式来自定制
7、slots 属性
用法举例:
此方法用得少,用的时候慎用
8、__doc __ ——文档描述信息
该属性无法被继承
9、__module __和__class __ ——查看对象来自于哪一个模块或类
10、__del __ ——析构方法
结论:从上面三个结果中看出,只有实例被删除的时候才会触发 __del __ ;单单删除实例下的属性不会触发;文件执行完毕,实例被回收,触发__del __。
11、__call __
foo 虽然是一个类,但是也是一个对象(既然是对象,就有另外一个类来产生)
12(1)、__iter __ 与 __next __ ——迭代器协议
其它的暂略… …
12(2)、迭代器协议实现斐波那契数列
二、描述符(__get __、__set __、__delete __)
普通开发中用不到,开发大型的框架,给别人用的时候才用得到
1、描述符的定义
2、描述符的作用
描述符的作用:是用来代理另外一个类的属性(必须把描述符定义成这个类的类属性,不能定义到构造函数中)
从上图中看到,无论怎么调用,都无法触发里面的方法,问题在于,描述符是代理另外一个类的属性,所以,必须要其他的类来调用,才能触发。看下图:
上图中看到,必须是有其他的类来调用描述符,才能触发描述符方法
3、两种描述符
描述符分两种
注意事项:
一、描述符本身应该定义成新式类,被代理的类也应该是新式类
二、必须把描述符定义成这个类的类属性,不能定义为构造函数中
比如上图这个,定义成这种就不行,什么都不会触发。再看下图:
这种是可以触发的。在上图 类hoo 当中,x被 foo 描述了,所以凡是关于 x 的操作都是 foo的操作 ;x被 foo 代理了。
三、要严格遵循该优先级,优先级由高到低分别是:
1.类属性
2.数据描述符
3.实例属性
4.非数据描述符
5.找不到的属性触发__getattr__()
原文链接:https://blog.csdn.net/qq_41824825/article/details/111641808