zoukankan      html  css  js  c++  java
  • 第四十三篇 面向对象进阶2

    第四十三篇 面向对象进阶2

    一、类的封装

    封装:打包,封起来,装起来

    1.封装分为两个层面

    1.第一个层面:对象能拿到类的东西,但是类能拿到对象的东西吗?这里就存在一层封装

    class Foo():
    	count = 0
    	print(count)
    
    f = Foo()
    print(f.count)  # 0
    f.name = 'nick'  # 对对象进行了封装
    print(Foo.name)
    

    2.第二个层面的:内部可以使用,外部不可以使用,在你需要封装的属性前面加上__

    class People():
    	__love_people = 'male'
    	print('in',love_people)
    
    	def __nawan(self):
    		print('nawan')
    	def __nakuaizi(self):
    		print('nakuaizi')
    	def __chifan(self):
    		print('chifan')
    
    	def chifan_all(self):
    		self.__nawan()
    		self.__nakuaizi()
    		self.__chifan()
    
    print('out',People.__f1)
    
    p  = People()
    print('out',p.nawan())
    print('out',p.nakuaizi())
    print('out',p.chifan())
    
    print('out',p.chifan_all())
    

    3.对属性这个封装有什么用:藏起来了,保护了你的隐私,类内部的属性不想让其他人访问
    4.对方法封装有什么好处:精简了代码,你吃饭就使用chifan这个方法就行了,不需要去关心其他的操作,并且外部调用者也不知道你内部发生了什么

    2.应用

    print('*'*50)
    class People:
    	def __init__(self,pwd):
    		self.__pwd = pwd
    	@property  # 方法不用加括号使用
    	def pwd(self):
    		return f'无法获取你的密码'
    
    p = People('123')
    print(p.pwd)
    print(p.pwd)
    
    class F1:
        __count = 0
    
    f = F1()
    print(f._F1__count)  # 如果你真的要拿,_类名__属性去拿(不可能这样做)
    
    class Foo:
        def f1(self):
            print('FOO.f1')
        def f2(self):  # foo
            print('Foo.f2')
            self.f1()
    
    class Bar(Foo):
        def f1(self):
            print('Bar.f1')
    
    foo = Bar()
    foo.f2() # Foo.f2  # Bar.f1
    
    class Foo:
        def __f1(self):  # _Foo__f1
            print('FOO.f1')
        def f2(self):  # foo
            print('Foo.f2')
            self.__f1()  # _Foo__f1
    print(Foo.__dict__)
    class Bar(Foo):
        def __f1(self):  # _Bar__f1
            print('Bar.f1')
    
    bar = Bar()
    bar.f2() # Foo.f2
    # 封装其实在定义阶段就以己经执行了,会把私有属性__f1变成_Foo__f1,之后都不会做这种处理
    
    class Foo():
        __count = 0
    
    foo = Foo()
    print(foo)
    
    
    foo.__y = 1
    print(foo.__y)
    

    二、类的property特性

    1. BMI(Body Mass Index):身体体质指数

    男性体脂>25%,女性>33%是诊断为肥胖的标准

    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.8,70)
    print(peo.height)
    print(peo.bmi())
    print(peo.bmi)
    

    2.装饰器用法(只在Python3中使用)

    1.property一般用在:本来是方法,但是他应该是属性的时候,我们就应该property

    2.setattr 和 delattr

    3.setattr 和 delattr这两个方法只能对属性修改和删除,也就是在使用了property之后使用

    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(f'你已经成功修改为{value}')
    
        @bmi.deleter  # 在删除bmi的时候触发,不能加参数
        def bmi(self):
            print('delter')
    
    peo = People(1.8,70)
    print(peo.bmi)
    
    print('*'*50)
    peo.bmi = 50
    
    print('*'*50)
    del peo.bmi
    

    类属性用法(Python2的)

    三、类与对象的绑定方法及非绑定方法

    1.绑定方法:绑定的方法

    class Foo:
        # 绑定给对象,只有对象能用,但是类也能使用,使用的时候必须得传参
        def f1(self):
            print(self)
    
        @classmethod  # 让被装饰的函数给类使用,约定俗称参数为cls
        # 绑定给类的方法,类能使用,对象也可以使用,但是参数依然是类
        def f2(cls):
            print(cls)
    
        # 什么都不绑定的,非绑定方法,定义了普通的函数
        @staticmethod
        def f3(self):
            print(self)
    
    f = Foo()
    f.f1()
    Foo.f1(1111)
    
    print('*' * 50)
    Foo.f2()
    f.f2()
    
    print('*'*50)
    Foo.f3(2222)
    f.f3(2222)
    

    2.什么时候使用?

    • 这个方法需要使用类做为参数的时候就得使用类绑定方法,@classmethod
    class A:
        def __init__(self,name):
            self.name = name
    
        @classmethod
        def cla_pri(cls):
            print(f'{cls.__name__},{cls}')
    
    class B(A):
        pass
    
    A.cla_pri()
    B.cla_pri()
    x = B('x')
    x.cla_pri()
    '''
    A,<class '__main__.A'>
    B,<class '__main__.B'>
    B,<class '__main__.B'>
    
    '''
    
    • 这个方法需要使用对象作为参数的时候就得使用对象绑定方法
    • 这方法即不需要类作为参数又不需要对象作为参数,使用非绑定方法,@staticmethod

    四、总结

    1.封装:隐藏属性或方法,外部无法使用,内部可以使用,在类定义阶段就执行了,真的想引用,就使用_类名__属性名

    2.隐藏模块内的函数/变量_x:from module import *(无法导入), from module import _x(不合理)

    3.@property:被 @property 装饰的函数会从函数变成属性,也就是说直接.函数名,不需要加括号使用

    4.@方法名.setter:被 @方法名.setter 装饰的函数,方法名修改,会执行这个装饰的函数

    @bmi.setter
    def set_bmi():
        print('setter')
    peo.bmi = 40
    

    5.@方法名.deleter:被 @方法名.deleter 装饰的函数,方法名删除,会执行这个装饰的函数

    @bmi.deleter
    def del_bmi():
        print('deleter')
    del peo.bmi
    

    6.python2中类属性调用的方法

    7.对象的绑定方法:没有加任何装饰的方法就是对象的绑定方法

    8.类的绑定方法:加了@classmethod装饰器的方法就是类的绑定方法

    9.非绑定方法:加了@staticmethod装饰器的方法就是非绑定方法,其实就是一个普通的函数

  • 相关阅读:
    hdu 1108 最小公倍数
    hdu 1106 排序
    hdu 1097 A hard puzzle
    hdu 1076 An Easy Task
    hdu 1064 Financial Management
    hdu 1061 Rightmost Digit
    hdu 1050 Moving Tables
    hdu 1060 Leftmost Digit
    hdu 1049 Climbing Worm
    hdu1104
  • 原文地址:https://www.cnblogs.com/itboy-newking/p/11072038.html
Copyright © 2011-2022 走看看