潭州课堂25班:Ph201805201 第十二课 new方法,定制属性访问,描述符与装饰器 (课堂笔记)

1,new方法:

  类每次实例化时都会创建一个新的对象,

class Textcls:
    #  cls 是指类本身,
    def __new__(cls, *args, **kwargs):      #  在 __init__ 前触发,
        if not hasattr( cls,'inst' ):       #   判断是否有 inst 的属性
            cls.inst = super().__new__(cls)   #     调用 __new__ 方法,为当前类创建空间
            #  如果没有  创建属性给实例,此时 属性= c1

        return cls.inst
        # 如果有 返回 c1, 此时 c1 =  c2

    def __init__(self):
        print('')

c1 = Textcls()   #  第一次实例 c1,   
c2 = Textcls()   #   第二次实例 c1 给c2
print(id(c1), id(c2))
#   创建两个实例 ,内存地址一样,所以两个实例拿完相同,
#    目的为了文件打开保存是一一的,

  

2,  定制属性访问     (自醒) 反射

  hasattr( cls,'inst' )    判断类 cls 中有没有 inst 的属性   存在返回 真

  delattr ( cls,'inst' )  删除类 cls  中的 inst  属性

  gelattr ( cls,'inst' )  获取类 cls  中的 inst  值,相当于:cls .inst  

  selattr ( cls,'inst','已经存在?' )  如果 inst  在类 cls 中已经存在,则会用 “已经存在?”这个值覆盖原 inst  的值 ,

                  如果不存在,则添加这个属性

  

  __getattr__():  的使用,

class Textcls:
    def __getattr__(self, item):
        print('你调用的属性不存在,')


c = Textcls()
getattr(c,'a')


##    ------》》》 你调用的属性不存在,

  如果一个不存在的属性被调用,则会触发 __getattr__(): 的方法

 

3,描述符

class MyAttribute:
    def __get__(self, instance, owner):
        print("get")

    def __set__(self, instance, value):
        print('set')

    def __delete__(self, instance):
        print("delete")

    def __del__(self):
        print('del')

class MyClass:
    m = MyAttribute()         #   用实例做属性
    def __del__(self):
        print('del  MyClass')

c = MyClass()
c.m                     #   调用属性,如果属性是个实例,会触发 __get__方法
#   一个实例调用另一个实例,

c.m = 123      #   修改实例属性时,果属性是个实例, 会触发 __set__
del c.m        #  修改实例属性时,会触发 __set__

  

4,装饰器 

def f1(f):
    print('f1')
    def f2():
        print('f2')
    return f2

def f():
    print('f')

f1(f)()


##   f1(f)()  相当于 
          #           a = f()
          #            f1(a)            

 

     f1()  返回 f2,这时 f1() 可以做另一个函数的 装饰def f1(f):

    print('f1')
    def f2():
        print('f2')
    return f2

@ f1    #  语法糖,如果后面是韩式,会直接调用这个函数,
def f():
    print('f')

f()   #  运行该函数时,相当于把这个函数当成参数传进 f1() 中运行,
  
#  再把返回的 闭包加 () 运行,

  

 

  内置装饰器:

   @property 

class Re():

    @property       #  调用该方法时不会传入  self
    def test1(self):
        print('a')

    def test2(self):
        print('b')

m = Re()
m.test1
m.test2()

@ classmethod
class Tacls():

    def f1(self):
        print(self)

    @ classmethod       #   会自动传入 类本身,
    def f2(cls):
        cls().f1()
        print('方法 f2')

m = Tacls()
m.f1()
m.f2()

  

@staticmethod 
class Re():

    @staticmethod       #  调用该方法时不会传入  self
    def test1(self):
        print('a')

    def test2(self):
        print('b')

m = Re()
m.test1(self=)

  

posted @ 2018-06-14 05:26  25班Ph201805201  阅读(145)  评论(0编辑  收藏  举报