Python基础课--第十三节 面向对象2

本文深入探讨Python中的特殊方法(魔术方法),如__init__的自动调用及作用,以及封装的概念,包括如何隐藏对象属性,使用getter和setter方法控制属性访问,实现数据安全性和验证。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

1 特殊方法(魔术方法)

  • 特殊方法都是以双下划线开头双下划线结尾的方法
  • 特殊⽅法都是形如 _ _ xxx _ _()这种形式
  • 特殊方法不需要我们自己调用
  • 特殊方法会在特殊的时候自动调用
  • 学习特殊方法
  1. 特殊方法什么时候调用
  2. 特殊方法有什么作用
  • 类中的代码块先执行,而且只执行了一次

创建流程

p1 = Person()

1.创建一个变量
2.在内存中创建一个新的对象
3.执行类中的代码块(只执行一次)
3.init(self)方法执行

class Person:



    # 在类中可以定义一些特殊方法()魔术方法
    # 特殊方法都是以双下划线开头双下划线结尾的方法
    # 特殊方法不需要我们自己调用
    def __init__(self):
        print('init方法执行了')

    print('Person代码块中的代码')


    def speak(self):

        print('大家好,我是%s'%self.name)

p1 = Person()
p2 = Person()
p3 = Person()
p4 = Person()
结果
Person代码块中的代码
init方法执行了
init方法执行了
init方法执行了
init方法执行了

init在什么时候调用

  • init会在对象创建以后立即执行
  • init会像新创建的对象初始化属性
class Person:



    # 在类中可以定义一些特殊方法()魔术方法
    # 特殊方法都是以双下划线开头双下划线结尾的方法
    # 特殊方法不需要我们自己调用
    def __init__(self,name):
        # 通过self向新创建的对象中初始化属性
        self.name = name

        # print(self)
    #     print('init方法执行了')
    #
    # print('Person代码块中的代码')


    def speak(self):

        print('大家好,我是%s'%self.name)

p1 = Person('葫芦娃')

p2 = Person('钢铁侠')
p3 = Person('绿巨人')
p4 = Person('美国队长')

print(p1.name)
print(p2.name)
print(p3.name)
print(p4.name)

p2.speak()
结果
葫芦娃
钢铁侠
绿巨人
美国队长
大家好,我是钢铁侠

有上述例子得出,类的基本结构

# 类的基本结构
'''
class 类名([父名])

    公共的属性……
    
    # 对象的初始化方法
    def __init__(self,……)
    
        代码块
        
    # 其他的方法
    def m1(self,……)
        代码块
        
    def m1(self,……)
        代码块
        
    ……
'''
  • 我们要增加数据的安全性:

    属性不能随意修改(我让你改你才能改,不让你改你就别改)
    属性不能改为任意的值

2 封装

  • 封装是面向对象的三大特性之一
  • 封装指的是隐藏对象中一些不希望被外部访问到的属性或方法
  • 如何隐藏对象中的一个属性
    将对象的属性名,修改为一个外部不知道的名字
  • 如何获取(修改)对象当中的属性
    我们可以提供一个getter和setter方法是外部可以访问和修改属性
  • 使⽤封装,确实增加了类的定义的复杂程度,但是它也确保了数据的安全
  1. 隐藏属性名,使调⽤这⽆法随意的修改对象中的属性
  2. 增加了getter()和setter()⽅法,很好控制属性是否是只读的
  3. 使⽤setter()设置属性,可以增加数据的验证,确保数据是正确的
  4. 使⽤getter()⽅法获取属性,使⽤setter()⽅法设置属性可以在读取属
    性和修改属性的同时做⼀些其他的处理
class Dog:

    def __init__(self,name,age):

        self.hidden_name = name   # 隐藏名字
        self.hidden_age = age

    def speak(self):

        print('大家好,我是%s'%self.hidden_name)

    def get_age(self):         # getter方法

        # get_name()用来获取对象的name属性
        return self.hidden_age

    def set_age(self,age):

        # set_name()用来设置对象的name属性
        self.hidden_age = age

d = Dog('德牧',5)


d.set_age(8)
print(d.get_age())
结果
8

添加修改条件,验证了3. 使⽤setter()设置属性,可以增加数据的验证,确保数据是正确的

class Dog:

    def __init__(self,name,age):

        self.hidden_name = name   # 隐藏名字
        self.hidden_age = age

    def speak(self):

        print('大家好,我是%s'%self.hidden_name)

    def get_age(self):         # getter方法

        # get_name()用来获取对象的name属性
        return self.hidden_age

    def set_age(self,age):

        # set_age()用来设置对象的age属性
        if age > 0:
            self.hidden_age = age

d = Dog('德牧',5)


d.set_age(-8)
print(d.get_age())
结果
5
  1. 使⽤getter()⽅法获取属性,使⽤setter()⽅法设置属性可以在读取属
    性和修改属性的同时做⼀些其他的处理
class Dog:

    def __init__(self,name,age):

        self.hidden_name = name   # 隐藏名字
        self.hidden_age = age

    def speak(self):

        print('大家好,我是%s'%self.hidden_name)

    def get_age(self):         # getter方法

        # get_name()用来获取对象的name属性
        print('用户获取了属性')
        return self.hidden_age

    def set_age(self,age):

        # set_age()用来设置对象的age属性
        print('用户修改了属性')
        if age > 0:
            self.hidden_age = age

d = Dog('德牧',5)


d.set_age(8)
print(d.get_age())
结果
用户修改了属性
用户获取了属性
8
  • 可以为对象的属性使用双下划线开头–>__xxx
  • 双下划线开头的属性是对象的隐藏属性,隐藏属性只能在类的内部访问,无法通过外部访问

隐藏属性是python自动为属性改了一个名字

  • 实际改的名字是:_类名__属性名[^__name --> _Person__name]
# 实际改的名字是 _类名__属性名[^__name --> _Person__name]
class Person:

    def __init__(self,name):

        self.__name = name

    def get_name(self):

        return self.__name

    def set_name(self,name):

        self.__name = name

p = Person('葫芦娃')
print(p._Person__name)
# p.set_name('钢铁侠')

p._Person__name = '绿巨人'

print(p.get_name())
结果
葫芦娃
绿巨人
  • 一般你要告诉别人这个属性是用来封装的 以 _开头
# 一般你要告诉别人这个属性是用来封装的 以 _开头
class Person:

    def __init__(self,name):

        self._name = name

    def get_name(self):

        return self._name

    def set_name(self,name):

        self._name = name

p = Person('葫芦娃')
# print(p._Person__name)
# # p.set_name('钢铁侠')

# p._Person__name = '绿巨人'

# print(p.get_name())

print(p._name)
结果
葫芦娃
  • 一般情况,使用_开头的属性都是私有属性,没有特殊情况下不要修改私有属性

3 @property

  • 我们可以使⽤@property装饰器来创建只读属性,@property装饰器会将⽅法转换为相同名称的只读属性,可以与所定义的属性配合使⽤,这样可以防⽌属性被修改
  • property装饰器 用来将一个方法转换为对象的属性
    这个防止属性被修改
class Person:

    def __init__(self,name):

        self._name = name   # 对name做了封装
    # property装饰器 用来将一个方法转换为对象的属性
    @property
    def name(self):
        print('getter方法执行了')

        # 这是一个getter()方法
        return self._name

p = Person('葫芦娃')

# p.name = '钢铁侠'   # AttributeError: can't set attribute 防止属性被修改

# print(p.name())    # TypeError: 'str' object is not callable
print(p.name)
结果
getter方法执行了
葫芦娃

如果想改怎么办

class Person:

    def __init__(self,name):

        self._name = name   # 对name做了封装
    # property装饰器 用来将一个方法转换为对象的属性
    @property
    def name(self):
        print('getter方法执行了')

        # 这是一个getter()方法
        return self._name

    # setter 方法的装饰器 @属性名.setter
    @name.setter
    def name(self,name):

        self._name = name

p = Person('葫芦娃')

p.name = '钢铁侠'   

print(p.name)
结果
getter方法执行了
钢铁侠

添加property装饰器以后,我们就可以像调用属性一个调用方法

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值