私有属性与私有方法
应用场景
- 在实际开发中,对象的某些属性或者方法 可能只希望在对象的内部被使用,而不希望在外部被访问到;
- 私有属性 就是对象不希望公开的属性;
- 私有方法 就是对象不希望公开的方法;
定义方式
在定义属性或者方法时,在属性名或者方法名前面增加两个下划线,定义的就是私有属性或方法;
没使用私有属性前
class Women:
def __init__(self, name, age):
self.name = name
self.age = age
def secret(self):
print("%s 的年龄是 %d" % (self.name, self.age))
xiaohong = Women("小红", 18)
print(xiaohong.age) # 18
xiaohong.secret() # 小红 的年龄是 18
使用私有属性后
class Women:
def __init__(self, name, age):
self.name = name
self.__age = age
def secret(self):
print("%s 的年龄是 %d" % (self.name, self.__age))
xiaohong = Women("小红", 18)
# 不能在外部直接通过对象调用私有属性
# print(xiaohong.age) # 报错 AttributeError: 'Women' object has no attribute 'age'
# 但还是能通过内部方法调用对象的私有属性
xiaohong.secret() # 小红 的年龄是 18 公有方法还是能够调用私有属性
使用私有方法后
class Women:
def __init__(self, name, age):
self.name = name
self.__age = age
def __secret(self):
print("%s 的年龄是 %d" % (self.name, self.__age))
xiaohong = Women("小红", 18)
# 当设置私有方法后,外部就不能调用私有方法了
# xiaohong.__secret() # 报错 AttributeError: 'Women' object has no attribute '__secret'
伪私有属性和方法
在python中,并没有真正意义上的私有,只有伪私有;
- python在给私有属性和私有方法命名时,实际是对名称做了一些特殊处理,是的外界无法访问到;
- 处理方式:在名称前加上 _类名,即 _类名__名称
破解私有属性和私有方法
class Women:
def __init__(self, name, age):
self.name = name
self.__age = age
def __secret(self):
print("%s 的年龄是 %d" % (self.name, self.__age))
xiaohong = Women("小红", 18)
# 当设置私有方法后,外部就不能直接调用私有方法了
# xiaohong.__secret() # 报错 AttributeError: 'Women' object has no attribute '__secret'
# 破解私有属性和私有方法,但不建议使用
print(xiaohong._Women__age) # 18
xiaohong._Women__secret() # 小红 的年龄是 18
但注意,在日常开发中,不要使用这种方式访问对象的私有属性或者私有方法!!我们只需要用提供的公共方法来简介调用私有方法或属性即可。
父类的私有属性和方法
- 子类对象不能在自己的方法内部,直接访问父类的私有属性和私有方法;
- 子类对象可以通过父类的共有方法,间接访问到私有属性和私有方法。
私有属性,方法,是对象的隐私,不对外公开,外界以及子类,都不能直接访问;
私有属性,方法通常用来做一些内部的事情;
子类对象,可以调用父类的公有方法和公有属性;
而如果父类中的公有方法 有调用父类的私有属性的话,那么我们也可以通过调用父类的公有方法来间接调用父类的私有属性和方法。
class Women:
def __init__(self, name, age):
self.name = name
self.__age = age
def __secret(self):
print("私有:%s 的年龄是 %d" % (self.name, self.__age))
def public(self):
print("公有:%s 的年龄是 %d" % (self.name, self.__age))
self.__secret()
class Girl(Women):
def test(self):
print("你的姓名是 %s" % self.name)
# print("你的年龄是 % d" % self.__age) # 不能在子类中直接调用父类的私有属性
# self.__secret() # 不能在子类中直接调用父类的私有方法
# 可以通过调用父类的公有方法来简介调用父类的私有属性和方法
self.public() # 运行结果:(公有:xiaohong 的年龄是 18 私有:xiaohong 的年龄是 18)
print("...")
xiaohong = Girl("xiaohong", 18)
# 子类的对象不能在外部直接调用父类/祖父类的私有属性和方法
# print(xiaohong.__age)
# print(xiaohong.__secret)
xiaohong.test()