• 类和对象6:相关内置函数


    目录

    1. issubclass(class, classinfo)

    2. isinstance(object, classinfo)

    3. hasattr(object, name)

    4. getattr(object, name[, default])

    5. setattr(object, name, value)

    6. delattr(object, name)

    7. property(fget=None, fset=None, fdel=None, doc=None)

    8. property的修饰符实现方法


    1. issubclass(class, classinfo)

    判断 class 是否为 classinfo 的一个子类,是则返回 True,否则返回 False;

    一个类可以认为是自身的子类;

    一个类父类的父类或更高层级的父类,都可以认为是自身的父类;

    class 必须为一个类对象,否则报错;classinfo 可以是类对象,也可以是类对象组成的元组,否则报错;

    classinfo 为类对象元组时,class 只要是其中任意一个类对象的子类,则返回 True;

    有多个父类的子类,只需要 classinfo 中有其中一个父类,则返回True;

    1. #创建父类
    2. class Base1:
    3. def __init__(self,name='Base1'):
    4. self.name1 = name
    5. def showname1(self):
    6. print(f'名字为:{self.name1}')
    7. class Base2:
    8. def __init__(self,name='Base2'):
    9. self.name2 = name
    10. def showname2(self):
    11. print(f'名字为:{self.name2}')
    12. class Base3:
    13. def __init__(self,name='Base3'):
    14. self.name3 = name
    15. def showname3(self):
    16. print(f'名字为:{self.name3}')
    17. #创建子类
    18. class Derived1(Base1):
    19. pass
    20. class Derived2(Base2,Base3):
    21. pass
    22. class Derived3(Derived1):
    23. pass
    24. #判断 class 是否为 classinfo 的一个子类,是则返回 True,否则返回 False
    25. issubclass(Derived1,Base1)
    26. True
    27. issubclass(Derived1,Base2)
    28. False
    29. #一个类可以认为是自身的子类
    30. issubclass(Derived1,Derived1)
    31. True
    32. #一个类父类的父类或更高层级的父类,都可以认为是自身的父类
    33. issubclass(Derived3,Base1)
    34. True
    35. #classinfo 可以类对象组成的元组,class 只要是其中任意一个类对象的子类,则返回 True
    36. issubclass(Derived1,(Base1,Base2))
    37. True
    38. #有多个父类的子类,只需要 classinfo 中有其中一个父类,则返回True
    39. issubclass(Derived2,Base2)
    40. True
    41. issubclass(Derived2,Base3)
    42. True
    43. #class 不是类对象报错
    44. issubclass((Derived1,Derived2),Base1)
    45. Traceback (most recent call last):
    46. File "<input>", line 1, in <module>
    47. TypeError: issubclass() arg 1 must be a class
    48. #classinfo 不是类对象或元组报错
    49. issubclass(Derived1,[Base1,Base2])
    50. Traceback (most recent call last):
    51. File "<input>", line 1, in <module>
    52. TypeError: issubclass() arg 2 must be a class or tuple of classes

    2. isinstance(object, classinfo)

    判断 object 是否为 classinfo 的一个实例对象,是则返回 True,否则返回 False;

    object 是 classinfo 中某个类对象的子类或更下层的子类的子类等,仍返回True;

    object 必须为一个实例对象,否则返回 False;classinfo 可以是类对象,也可以是类对象组成的元组,否则报错;

    classinfo 为类对象元组时,object 只要是其中任意一个类对象的实例对象,则返回 True;

    1. #创建的类见章节1. issubclass
    2. #创建实例对象
    3. base11 = Base1()
    4. base12 = Base1()
    5. base13 = Base1()
    6. base21 = Base2()
    7. derived11 = Derived1()
    8. derived12 = Derived1()
    9. derived21 = Derived2()
    10. derived31 = Derived3()
    11. #判断 object 是否为 classinfo 的一个实例对象,是则返回 True,否则返回 False
    12. isinstance(base11,Base1)
    13. True
    14. isinstance(base21,Base1)
    15. False
    16. isinstance(base12,Base1)
    17. True
    18. #object 是 classinfo 中某个类对象的子类或更下层的子类的子类等,仍返回True
    19. isinstance(derived11,Base1)
    20. True
    21. isinstance(derived21,Base1)
    22. False
    23. isinstance(derived31,Base1)
    24. True
    25. isinstance(derived21,Base2)
    26. True
    27. isinstance(derived21,Base3)
    28. True
    29. #classinfo 为类对象元组时,object 只要是其中任意一个类对象的实例对象,则返回 True
    30. isinstance(derived31,(Base1,Base3))
    31. True
    32. #class 必须为一个实例对象,否则返回 False
    33. isinstance(Base1,Base1)
    34. False
    35. isinstance(Derived1,Base1)
    36. False
    37. isinstance(derived11.name1,Base1)
    38. False
    39. isinstance(derived11.showname1,Base1)
    40. False
    41. #classinfo 可以是类对象,也可以是类对象组成的元组,否则报错
    42. isinstance(derived31,[Base1,Base3])
    43. Traceback (most recent call last):
    44. File "<input>", line 1, in <module>
    45. TypeError: isinstance() arg 2 must be a type or tuple of types

    3. hasattr(object, name)

    判断实例对象 object 中是否有属性名为 name 的变量或方法,是则返回 True,否则返回 False;

    object 必须为一个实例对象,否则返回 False;

    name 为变量或方法名的字符串,否则报错;

    可以认为是将实例对象 object 及其类对象的 '__dict__' 属性中所有的键与 'name' 做比对,判断是否与其中一个键值相等。

    1. #创建的类见章节1. issubclass
    2. #创建实例对象见章节2. isinstance
    3. #实例对象与创建实例的类对象的 '__dict__' 属性
    4. base11.__dict__
    5. {'name1': 'Base1'}
    6. Base1.__dict__
    7. mappingproxy({'__module__': '__main__', '__init__': <function Base1.__init__ at 0x00000218364AB040>, 'showname1': <function Base1.showname1 at 0x00000218364AB160>, '__dict__': <attribute '__dict__' of 'Base1' objects>, '__weakref__': <attribute '__weakref__' of 'Base1' objects>, '__doc__': None})
    8. #判断实例对象 object 中是否有属性名为 name 的变量或方法,是则返回 True,否则返回 False
    9. hasattr(base11,'name1')
    10. True
    11. hasattr(base11,'showname1')
    12. True
    13. hasattr(base11,'__init__')
    14. True
    15. hasattr(base11,'__dict__')
    16. True
    17. hasattr(base11,'__doc__')
    18. True
    19. #object 为类对象,返回 False
    20. hasattr(Base1,'name1')
    21. False
    22. #name 不是字符串,报错
    23. hasattr(base11,name1)
    24. Traceback (most recent call last):
    25. File "<input>", line 1, in <module>
    26. NameError: name 'name1' is not defined

    4. getattr(object, name[, default])

    返回实例对象 object 中,属性名为 name 的变量或方法;

    object 中不存在名为 name 的变量或方法,则default 可选参数已赋值返回 default 值,default 未赋值报错;

    可以认为是将实例对象 object 及其类对象的 '__dict__' 属性中所有的键与 'name' 做比对,如有对应的键,返回该键相应的值。

    1. #创建的类见章节1. issubclass
    2. #创建实例对象见章节2. isinstance
    3. #返回实例对象 object 中,属性名为 name 的变量
    4. getattr(derived11,'name1')
    5. 'Base1'
    6. #返回实例对象 object 中,属性名为 name 的方法
    7. getattr(derived11,'showname1')
    8. <bound method Base1.showname1 of <__main__.Derived1 object at 0x00000218364A6370>>
    9. x = getattr(derived11,'showname1')
    10. x()
    11. 名字为:Base1
    12. #不存在名为 name 的变量或方法,则default 可选参数已赋值返回 default 值
    13. getattr(derived11,'name2','实例中没有该属性!')
    14. '实例中没有该属性!'
    15. #不存在名为 name 的变量或方法,default 未赋值报错
    16. getattr(derived11,'name2')
    17. Traceback (most recent call last):
    18. File "<input>", line 1, in <module>
    19. AttributeError: 'Derived1' object has no attribute 'name2'

    5. setattr(object, name, value)

    设置实例对象 object 中,属性名为 name 的变量或方法的值为 value;

    object 中不存在名为 name 的变量或方法,则新建变量或方法并赋值为 value;

    可以认为是将实例对象 object 及其类对象的 '__dict__' 属性中所有的键与 'name' 做比对,如有对应的键,设置该键的值为 'value';没有对应的键,则新建键值对 'name : value';

    该方法可设置类中变量,新设置类的方法则会因 self 参数或修饰符导致调用失败;

    1. #创建的类见章节1. issubclass
    2. #创建实例对象见章节2. isinstance
    3. #设置修改类中变量
    4. derived21.showname2()
    5. 名字为:Base2
    6. setattr(derived21,'name2','TEST')
    7. derived21.showname2()
    8. 名字为:TEST
    9. derived21.name2
    10. 'TEST'
    11. #设置类中不存在的变量,新增变量属性
    12. setattr(derived21,'nametest','nameTEST')
    13. derived21.nametest
    14. 'nameTEST'
    15. #设置修改类中方法为实例方法
    16. def shownametest2(self):
    17. print(derived21.nametest + '2')
    18. setattr(derived21,'showname2',shownametest2)
    19. #设置成功,调用失败报错
    20. shownametest2
    21. <function shownametest2 at 0x00000218364A84C0>
    22. derived21.__dict__
    23. {'name2': 'TEST', 'nametest': 'nameTEST', 'showname2': <function shownametest2 at 0x00000218364A84C0>}
    24. derived21.showname2()
    25. Traceback (most recent call last):
    26. File "<input>", line 1, in <module>
    27. TypeError: shownametest2() missing 1 required positional argument: 'self'
    28. #设置修改类中方法为静态方法,调用报错
    29. @staticmethod
    30. def shownametest():
    31. print(derived21.nametest)
    32. setattr(derived21,'showname2',shownametest)
    33. derived21.showname2()
    34. Traceback (most recent call last):
    35. File "<input>", line 1, in <module>
    36. TypeError: 'staticmethod' object is not callable

    6. delattr(object, name)

    删除实例对象 object 中,属性名为 name 的变量或方法,如果变量或方法不存在,报错;

    可以认为是将实例对象 object 及其类对象的 '__dict__' 属性中所有的键与 'name' 做比对,如有对应的键,删除该键值对,没有则报错;

    无法删除不在实例对象 '__dict__' 中属于类对象的变量或方法。

    1. #创建类
    2. class Base:
    3. info = '123456'
    4. def __init__(self,name='Base'):
    5. self.name = name
    6. def showname(self):
    7. print(f'名字为:{self.name}')
    8. class Derived(Base):
    9. info = 'abcdef'
    10. def showname(self,name2):
    11. print(f'名字由:{self.name},变为:{name2}')
    12. #创建实例对象
    13. derived = Derived('Test')
    14. derived.showname('Test2')
    15. 名字由:Test,变为:Test2
    16. derived.info
    17. 'abcdef'
    18. #实例对象 '__dict__' 属性
    19. derived.__dict__
    20. {'name': 'Test'}
    21. #删除实例对象变量 name,删除后无法调用
    22. derived.name
    23. Traceback (most recent call last):
    24. File "<input>", line 1, in <module>
    25. AttributeError: 'Derived' object has no attribute 'name'
    26. #删除实例对象对应的类对象变量或方法,失败
    27. delattr(derived,'showname')
    28. Traceback (most recent call last):
    29. File "<input>", line 1, in <module>
    30. AttributeError: showname
    31. delattr(derived,'info')
    32. Traceback (most recent call last):
    33. File "<input>", line 1, in <module>
    34. AttributeError: info
    35. delattr(derived,'name')

    7. property(fget=None, fset=None, fdel=None, doc=None)

    property 返回一个类的属性 attribute,创建实例对象后,实例对象通过该属性调用赋值给 fget、fset、fdel 三个参数的方法,实现读取、设置、删除三种操作;

    实例.attribute 将调用 getter,实现读取;

    实例.attribute = value 将调用 setter,实现设置;

    del  实例.attribute 将调用 deleter,实现删除;

    当编码时,需要维护修改类中的读取、设置、删除方法时,只需要改变 property 中参数赋值的方法,调用 property 返回属性的其他代码无需改动。

    1. #创建类
    2. class Testproperty:
    3. def __init__(self,num):
    4. self.num = num
    5. def getnum(self):
    6. return self.num
    7. def setnum(self,value):
    8. self.num = value
    9. def delnum(self):
    10. del self.num
    11. #类中定义调用 property 函数的属性
    12. testattr = property(getnum, setnum, delnum, 'test property!')
    13. #创建实例,检查实例变量
    14. test = Testproperty(5)
    15. test.num
    16. 5
    17. #通过 property 返回属性 testattr 做读取
    18. test.testattr
    19. 5
    20. #通过 property 返回属性 testattr 做设置
    21. test.testattr = 10
    22. test.num
    23. 10
    24. #通过 property 返回属性 testattr 做删除
    25. del test.testattr
    26. test.num
    27. Traceback (most recent call last):
    28. File "<input>", line 1, in <module>
    29. AttributeError: 'Testproperty' object has no attribute 'num'

    8. property的修饰符实现方法

    除了直接调用 property 函数,也可以通过 property 的修饰符实现同样的效果。

    1. #创建与章节7. property 相同效果的类
    2. class Testproperty:
    3. def __init__(self,num):
    4. self.num = num
    5. @property
    6. def testattr(self):
    7. '''test property!'''
    8. return self.num
    9. @testattr.setter
    10. def testattr(self,value):
    11. self.num = value
    12. @testattr.deleter
    13. def testattr(self):
    14. del self.num
    15. #执行读取、设置、删除,效果一致
    16. test = Testproperty(5)
    17. test.num
    18. 5
    19. test.testattr
    20. 5
    21. test.testattr = 10
    22. test.num
    23. 10
    24. del test.testattr
    25. test.num
    26. Traceback (most recent call last):
    27. File "<input>", line 1, in <module>
    28. AttributeError: 'Testproperty' object has no attribute 'num'
  • 相关阅读:
    Supervisor启动并管理Celery相关进程
    【2021集创赛】基于arm Cortex-M3处理器与深度学习加速器的实时人脸口罩检测 SoC
    Unity反编译:IL2CPP 打包输出的cpp文件和dll(程序集)位置、Mono打包输出的dll(程序集)位置
    Svelte框架结合SpreadJS实现表格协同文档
    JMeter笔记15 | JMeter场景运行
    编程规范解决方案之ESLint + Git Hooks
    【软件测试】公司招个测试员,我又面试了100多人,结局......
    排障:记录一次NFS无法共享
    逆向破解之易语言按钮事件特征码
    JAVA-链式编程
  • 原文地址:https://blog.csdn.net/davidksatan/article/details/125534251