特殊方法
概念
在类中可以定义一些特殊方法,特殊方法形如__开头 __结尾的方法,特殊方法不需要我们自己调用,会在对象从创建以后立即执行。
(可以理解为其他语言中的构造函数或初始化函数,但又与之有一定区别),例如:
class Person():
def __init__(self,name):
# 通过self向新创建的对象来初始化属性
self.name = name
print('Person代码块中的代码') #类对象对应的代码在特殊方法之前执行
def speak(self):
print('大家好,我是%s'%self.name)
p1 = Person('小白') #特殊方法能够避免在外部进行修改时将类似name这种必要且可修改参数遗漏
p1.speak()
完整的类
class 类名([父类]):
# 对象的初始化方法
def __init__(self,.....):
......
# 其他的方法
def method1(self,.....):
...
def method2(self,.....):
...
封装
封装的原因
目前我们可以根据对象.属性的方式来修改属性的值,这种方式会使我们的属性非常不安全
class Person():
def __init__(self,name):
self.name = name
def speak(self):
print('大家好,我是%s'%self.name)
p1 = Person('小白')
p1.name='老白' #在外部修改依旧会修改属性值
p1.speak() #大家好,我是老白
所以我们需要一种增强数据的安全性的方式
1.属性不能随意修改
2.属性不能修改成任意的值
封装的概念
封装是面向对象的三大特性之一,是指隐藏对象中一些不希望被外界访问到的属性和方法。
简单封装对象
将对象的属性名修改成一个外部不知道的名字
class Person():
def __init__(self,name):
self.hidden_name= name #此处hidden_name便是弱封装之后的属性
def speak(self):
print('大家好,我是%s'%self.hidden_name)
p1 = Person('小白')
p1.speak()
双下划线开头的属性,是对象的隐藏属性,隐藏属性只能在类的内部访问,无法通过对象访问,其实隐藏属性只不过是Python自动的为属性改了一个名字,实际上它是将名字修改成了 _类名__属性名 。
class Person():
def __init__(self,name):
self.__name = name #__name--> _Person__name
def speak(self):
print('大家好,我是%s'%self.__name)
p = Person('小白')
#print(p.__name) #调用不到
p.speak()
封装的访问方法
封装后的对象可通过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_name(self):
# get_name是用来获取对象的name属性
return self.hidden_name
def set_name(self,name):
# set_name()是用来设置对象的name属性
self.hidden_name = name
def get_age(self):
# get_age是用来获取对象的age属性
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(10)
print(d.get_age())
封装的作用
使用封装,确实增加了类定义的复杂程度,但是它也确保了数据的安全
1.隐藏了属性名,使使用者无法随意修改对象中的属性
2.增加了getter和setter方法,很好控制属性是否只读
如果希望属性只读的,则可以直接去调用getter方法
如果使用setter方法,可以增加数据的验证。确保数据的值是正确的
3.使用setter方法的时候我们在修改数据的同时也可以做一些其他的操作
property装饰器
概念
@property用来创建只读属性 @property装饰器会将方法转换为相同名称的只读属性
class Person():
def __init__(self,name):
self._name = name
@property #可将name读取方法转换成name只读属性
def name(self):
print('get方法执行了')
return self._name
# setter方法的装饰器 @属性名.setter
@name.setter #将name修改方法转换成name修改属性
def name(self,name):
print('set方法执行了')
self._name = name
p = Person('葫芦娃')
p.name = '超人' #这里不是对属性赋值,而是调用setter方法
print(p.name) #这里是调用getter方法