• 类和对象1:基础学习


    目录

    1. 类和实例

    2. 实例对象

    3. Python 中的对象

    4. self 参数

    5. __init__() 方法

    6. 类的公有/私有


    1. 类和实例

    OOP编程:Object-Oriented Programming 面向对象编程,有三个基本特征——封装、继承、多态。

    • 封装:对外部隐藏对象的工作细节
    • 继承:子类自动共享父类数据和方法的机制
    • 多态:可以对不同类的对象调用相同的方法,产生不同的结果

    为了让程序更易用,经常需要将多种数据、代码语句等封装为函数、模块等,面向对象即需要对数据和代码同时做封装。Python中的对象,即可以认为:

    对象=属性+方法

    其中,对象的特征称为“属性”,对象的行为称为“方法”。

    Python中,使用类(class)来定义对象的属性和方法,实用类创建的对象则称为这个类的一个实例(instance),两者定义如下:

    • 类(class):实例工厂。类定义对象的属性和方法,对象的属性通常由赋值语句添加到类中,对象的方法则通常是类中定义的各个函数,所有从类创建的实例都可继承该类的属性和方法。
    • 实例(instance):也称为实例对象(instance objects),代表程序领域中具体的元素,每个实例单独记录各自的数据。

    2. 实例对象

    实例对象继承了类定义的属性和方法,即实例可以调用类定义的变量和函数;

    实例对象单独记录自己的数据,修改实例对象某个变量后,其他实例对象不因此而改变;

    实例对象可以在类的基础上增加新的赋值语句,并可以通过 dir() 查询;

    1. #类-tank
    2. class tank:
    3. Name = 'ZTZ-99A'
    4. Members = ['张三','李四','王五']
    5. def __init__(self,Armor=80,HP=100,Gun=125,Armor2=0,Gun2=0):
    6. self.Armor = Armor
    7. self.HP = HP
    8. self.Gun = Gun
    9. self.TargetArmor = Armor2
    10. self.TargetGun = Gun2
    11. def attack(self):
    12. damage = self.Gun - self.TargetArmor
    13. print(f'发起进攻,造成伤害{damage}')
    14. def defend(self):
    15. damage = self.TargetGun - self.Armor
    16. print(f'进行防御,受到伤害{damage}')
    17. if (self.HP - damage) <= 0:
    18. print('已阵亡')
    19. else:
    20. print(f'剩余血量{self.HP-damage}')
    21. #声明实例 tankNo1
    22. tankNo1 = tank()
    23. #可以调用类定义的变量和函数,并对其中变量数值做修改
    24. tankNo1.Name
    25. 'ZTZ-99A'
    26. tankNo1.attack()
    27. 发起进攻,造成伤害125
    28. tankNo1.TargetGun = 105
    29. tankNo1.defend()
    30. 进行防御,受到伤害25
    31. 剩余血量75
    32. ##声明实例 tankNo2
    33. tankNo2 = tank(Armor2=90,Gun2=120)
    34. tankNo2.attack()
    35. 发起进攻,造成伤害35
    36. #修改 tankNo2 实例数据,不影响 tankNo1 实例中数据
    37. tankNo2.Name = 'ZTZ-96A'
    38. tankNo2.Name
    39. 'ZTZ-96A'
    40. tankNo1.Name
    41. 'ZTZ-99A'
    42. #实例对象可以在类的基础上增加新的赋值语句,并可以通过 dir() 查询
    43. tankNo2.Ammunition = 50
    44. tankNo2.Ammunition
    45. 50
    46. dir(tankNo2)
    47. ['Ammunition', 'Armor', 'Gun', 'HP', 'Members', 'Name', 'TargetArmor', 'TargetGun', '__class__', '__delattr__', '__dict__', '__dir__', '__doc__', '__eq__', '__format__', '__ge__', '__getattribute__', '__gt__', '__hash__', '__init__', '__init_subclass__', '__le__', '__lt__', '__module__', '__ne__', '__new__', '__reduce__', '__reduce_ex__', '__repr__', '__setattr__', '__sizeof__', '__str__', '__subclasshook__', '__weakref__', 'attack', 'defend']

    3. Python 中的对象

    在Python中,整型变量是整数类的实例对象,字符串变量是字符串类的实例对象,列表、元组、字典、集合也类似。

    1. x = 100
    2. type(x)
    3. <class 'int'>
    4. dir(x)
    5. ['__abs__', '__add__', '__and__', '__bool__', '__ceil__', '__class__', '__delattr__', '__dir__', '__divmod__', '__doc__', '__eq__', '__float__', '__floor__', '__floordiv__', '__format__', '__ge__', '__getattribute__', '__getnewargs__', '__gt__', '__hash__', '__index__', '__init__', '__init_subclass__', '__int__', '__invert__', '__le__', '__lshift__', '__lt__', '__mod__', '__mul__', '__ne__', '__neg__', '__new__', '__or__', '__pos__', '__pow__', '__radd__', '__rand__', '__rdivmod__', '__reduce__', '__reduce_ex__', '__repr__', '__rfloordiv__', '__rlshift__', '__rmod__', '__rmul__', '__ror__', '__round__', '__rpow__', '__rrshift__', '__rshift__', '__rsub__', '__rtruediv__', '__rxor__', '__setattr__', '__sizeof__', '__str__', '__sub__', '__subclasshook__', '__truediv__', '__trunc__', '__xor__', 'as_integer_ratio', 'bit_length', 'conjugate', 'denominator', 'from_bytes', 'imag', 'numerator', 'real', 'to_bytes']
    6. x.real
    7. -1
    8. x.imag
    9. 0

    4. self 参数

    通常,类中所有方法(静态方法除外)的第一个参数,即 self 参数;

    同一个类可以生成无数个实例对象且各自独立,self 即代表类所创建的实例;

    self 用于将对象自身的引用作为第一个参数传给方法,帮助 Python 知道应该去操作类生成的哪个对象的方法;

    self 参数也可以使用其他参数名,但通常默认使用 'self'。

    1. class test:
    2. def printself(self):
    3. print(self)
    4. x = test()
    5. #self 和实例是同一个对象
    6. x.printself()
    7. <__main__.test object at 0x000001CBCA8A0CD0>
    8. x
    9. <__main__.test object at 0x000001CBCA8A0CD0>

    5. __init__() 方法

    __init__() 方法又称为构造方法,是Python中的又一种魔法方法,也是类中最常用的方法;

    __init__() 方法在实例对象创建时自动调用,并实现各类初始化传参、操作;

    __init__() 方法重写后添加的形参,如没有默认值,则在创建实例对象时必须填写实参,否则报错;

    __init__() 方法只能返回 None,返回其他对象报错。

    1. #创建重写 __init__() 方法的类
    2. class Test:
    3. def __init__(self, name, date, times):
    4. self.name = name
    5. self.date = date
    6. self.times = times
    7. def operater(self):
    8. print(f'{self.name}{self.date}去了{self.times}次小卖部!')
    9. #创建实例对象时,填入实参,完成初始化
    10. test1 = Test('小明','星期一','5')
    11. test1.name
    12. '小明'
    13. test1.operater()
    14. 小明在星期一去了5次小卖部!
    15. #创建实例对象时,部分参数未赋值,报错
    16. test2 = Test('小红','2022.1.1')
    17. Traceback (most recent call last):
    18. File "<input>", line 1, in <module>
    19. TypeError: __init__() missing 1 required positional argument: 'times'
    20. #只能返回 None,返回其他对象报错
    21. class Xtest:
    22. def __init__(self):
    23. return 'hi'
    24. testx = Xtest()
    25. Traceback (most recent call last):
    26. File "<input>", line 1, in <module>
    27. TypeError: __init__() should return None, not 'str'

    6. 公有/私有属性

    一般面向对象编程语言,都会区分公有和私有数据类型;

    Python 中默认对象的属性和方法都是公开的,可以直接通过点操作符 '.' 进行访问;为了实现私有变量和函数,Python 采用 Name Mangling(名字改编)技术,做了部分实现;

    Python 中的私有变量或函数,即在变量或函数名前加上 '_' 下划线,添加下划线后,变量/函数名外界无法直接访问;

    但 Python 采用的 Name Mangling(名字改编),实际上是把 '__变量/函数名',改编为了 '_类名__变量/函数名',实际上仍可以在外部通过后一种格式进行访问,是一种伪私有变量。

    1. #定义包含内部变量和内部函数的类
    2. class Test:
    3. __testinfo = 'testinfo'
    4. def __testfunc(self):
    5. print(f'{self.__testinfo}')
    6. #外部直接访问内部变量,失败
    7. test1 = Test()
    8. test1.__testinfo
    9. Traceback (most recent call last):
    10. File "<input>", line 1, in <module>
    11. AttributeError: 'Test' object has no attribute '__testinfo'
    12. #外部直接访问内部函数,失败
    13. test1.__testfunc()
    14. Traceback (most recent call last):
    15. File "<input>", line 1, in <module>
    16. AttributeError: 'Test' object has no attribute '__testfunc'
    17. #外部访问改编后的内部变量,成功
    18. test1._Test__testinfo
    19. 'testinfo'
    20. #外部访问改编后的内部函数,成功
    21. #内部函数可以直接调用内部变量,不需要使用改编后的变量名
    22. test1._Test__testfunc()
    23. testinfo

  • 相关阅读:
    高等工程数学 —— 第五章 (2)非线性规划的最优条件
    贝叶斯人工智能大脑与 ChatGPT
    【无标题】
    SpringBoot实战(二十四)集成 LoadBalancer
    C++ Reference: Standard C++ Library reference: Containers: deque: deque: rbegin
    MySql表的基本增删改查详解
    华为OD机试 - 玩牌高手 - 动态规划(Java 2023 B卷 100分)
    【C】为什么7.0会被存储为6.99999
    [ CTF ]【天格】战队WriteUp- 2022年第三届“网鼎杯”网络安全大赛(青龙组)
    【唠唠嵌入式】__嵌入式开发需要从0开始造轮子吗?
  • 原文地址:https://blog.csdn.net/davidksatan/article/details/125455691