类的三大特性---封装以及Property特性

类的封装

  • 封装:把一些属性,方法打包封装在一个对象中。

  • 对属性封装:保护隐私,类内部的属性不想让其他人访问

  • 对方法封装:对外隐藏内部具体的实现细节,外部只要根据内部提供的接口去用就可以了。

  • 封装分为两个层面

      1. 对象能拿到类的东西,但类能拿到对象的东西吗?
    class Foo:
        x = 1
        
    f = Foo()
    print(f.x)	# 1   对象可以获取类中的属性
    
    f.y = 2		# 这里就是对对象进行了封装
    print(Foo.y)
    1. 内部可以使用,但是外部不可以使用(在需要封装的属性前加上__
class People():
    __love_people = 'haha'
    print(__love_people)	# 内部可以使用
    
    def __zuofan(self):
        print('做饭')
       
   	def __xiwan(self):
        print('洗碗')
        
    def chifan(self):
        self.__zuofan()
        self.__xiwan()
        
f = People()
# print(f.__love_people)  # 报错,获取不到

f.chifan()
```

内部 haha
做饭
洗碗
```

应用场景:

class People:
    def __init__(self, pwd):
        self.__pwd = pwd	# 不想让别人获取密码
        
    @property    
    def pwd(self):		# 加一个伪装
        return '无法获取密码'
    
f = People(123)
print(f.pwd)    
无法获取密码

如果真的要拿

  • Python 的私有并不是真的私有,是一种称为name mangling 的改名策略
    • 可以使用object._classname__attributename访问
    • 也就是对象名._类名__属性名
class Foo:
    def f1(self):
        print('Foo.f1')
     
    def f2(self):
        print('Foo.f2')
        self.f1()		# b.f1()
        
class Bar(Foo):
    def f1(self):
        print('Bar.f1')
        
b = Bar()
b.f2()
Foo.f2
Bar.f1
class Foo:
    def __f1(self):
        print('Foo.f1')
    
    def f2(self):
        print('Foo.f2')
        self.__f1()		# b._Foo__f1()
        
class Bar(Foo):
    def __f1(self):
        print('Bar.f1')
        
b = Bar()
b.f2()   
Foo.f2
Foo.f1
  • 封装其实在定义阶段就已经执行了,会把私有属性__f1变成_Foo__f1,之后都不会做这种处理
class Foo:
    __count = 0
    
f = Foo()
f.__y = 1	# 这样只是定义了一个变量名叫__y,而不是把他变成了私有属性
print(f.__y)		# 所以可以运行使用
1

类的property特性

  • property一般用在类中写的是方法,但他应该按照属性来调用的时候,来进行使用。
  • property让函数方法变成属性
  • 举例:BMI
class People:
    
    def __init__(self, height, weight):
        self.height = height
        self.weight = weight
        
    @property	 	# 装饰器,下面方法的调用无需加()
    def bmi(self):
        return self.weight/(self.height**2)
    
peo = People(1.76, 62.5)
# print(peo.bmi())
print(peo.bmi)

setter & deleter

  • 装饰器用法,只在Python3中使用
  • @bmi.setter和@bmi.deleter让这个函数方法bmi()可以像属性一样进行修改和删除
  • 在修改或者删除的时候自动触发,运行下面方法的代码,不会执行原有的修改或者删除
class People:
    def __init__(self, height, weight):
        self.height = height
        self.weight = weight
        
    @property	 	# 装饰器,下面方法的调用无需加()
    def bmi(self):	
        return self.weight/(self.height**2)
    
    @bmi.setter		# 在修改bmi的时候出发,必须得加参数
    def bmi(self, value):	# 函数名不能改,否则报错
        print('你正在修改bmi')
        
    @bmi.deleter	# 在删除bmi的时候触发,不能加参数
    def bmi(self):
        print('你正在删除bmi')
        
peo = People(1.76, 62.5)
print(peo.bmi)

peo.bmi = 21
del peo.bmi

print(peo.bmi)
20.176911157024794
你正在修改bmi
你正在删除bmi
20.176911157024794

类属性用法

类与对象的绑定方法和非绑定方法

对象方法&类方法&静态方法

class Foo:
    # 对象方法不用加任何装饰
    def f1(self):		# 绑定给对象,实例对象使用的时候会自动传入self中,类也能用,但是需要传参
        print('对象方法')
        
    @classmethod		# 让被装饰的方法函数给类使用
    def f2(cls):		# 绑定给类,类对象使用的时候会自动传入cls中,对象也能用,但是传入的依旧是类
        print('类方法')
        
    @staticmethod		# 被装饰的方法函数变成非绑定的
    def f3():			# 生命都没绑定,也不会自动传参,就是正常的普通函数,类和对象都能用
        print('静态方法')

隐藏模块内的函数

  • 在想要隐藏的函数前加上 _即可,使用from module import *** 的时候无法导入,真要导入就from module impor _函数**(这样做没有意义)

封装的三个等级(课外了解)

  • 封装的三个级别:

    • 公开:public
    • 受保护的:protected
    • 私有的:private
    • 注意:public, protected, private 不是关键字,只是有概念
  • 判别对象的位置

    • 对象外部
    • 对象内部
    • 子类中
  • 私有的 private

    • 私有成员是最高级别的封装,只能在当前类或对象中访问
    • 在成员前面添加两个下划线即可
      • class Person():
        • name = "lingmei"
          • # name是共有成员
        • __age = 17
          • __age 是私有成员
    • Python 的私有并不是真的私有,是一种称为name mangling 的改名策略
      • 可以使用object._classname__attributename访问
      • 也就是对象名._类名__属性名
  • 受保护的封装 protected

    • 受保护的封装是将对象成员进行一定级别的封装,在类中或者子类中都可以进行访问,但在外部不可以
      • 类似于半私有半共有
    • 封装方法:在成员名称前面加一个下划线即可
  • 公开的、公共的 public

    • 公共的封装并没有对成员有什么操作
    • 任何地方都可以访问
原文地址:https://www.cnblogs.com/lucky75/p/11059969.html