• pyhon__new__方法.py


    # class A(object):
    #     def __init__(self, *args, **kwargs):
    #         print("init 方法id self {}".format(id(self)))
    #         self.attr = 'Hello, world!'
    #
    #     def __new__(cls, *args, **kwargs):
    #         print("new 方法id cls {}".format(id(cls)))
    #         self = object.__new__(cls)
    #         print("new 方法id self {}".format(id(self)))
    #         return self
    #
    #
    # onj = A()
    
    """
    运行结果
    new 方法id cls 2235268999616
    new 方法id self 2235301196752
    init 方法id self 2235301196752
    总结
    1、__new__和__init__之间的区别
        1、__nwe__创建实例对象之前被调用,实例化对象self,第一个参数cls到类对象被分配,
        2、__init__ 创建实例对象之后被调用,初始对象self ,第一个参数来自于实例对象被分配。
        3、__new__ 至少要一个参数 cls ,代表实例化的类,此参数是实例化的实话由python 解释器提供
        4、__new__ 必须有返回值,返回实例化cls出来的实例,还可以return 父类__new__出来的实例,或者直接object的__new__出来的实例
        5、__init__有一个参数self ,是由__new__出来的实例,__init__是在创建出实例的时候初始化了动作,不需要返回值。
    
    """


    """
    2.何时使用__new__?
        1、我想初始化不可变的 (不可变的是什么?https://www.cnblogs.com/Xingtxx/p/12819425.html)
        2、我想实现单列  (单例? https://www.cnblogs.com/Xingtxx/p/12819447.html)
        3、当你基于参数切换类 (元类引入? https://www.cnblogs.com/Xingtxx/p/12819412.html)
        4、使用namedtuple函数实际定义一个不可变的类.介绍__new__继承元组的不可变类的简单用法本页 https://docs.python.org/ja/3/library/collections.html#collections.namedtuple。
    """
    """
    3.创建实例。
        1、在研究继承元组的类之前,回顾super的动作。
        2、__new__该方法创建一个实例。 __init__该方法初始化实例。
    """
    
    # # __init__ 把实例slef 分配了给第一个参数,因此无需创建实例,只需要把属性分配给一个值
    # def __init__(self):  # <--- self 实例被代入
    #     print('__init__:', str(id(self)))
    #     self.attr = 'Hello, world!'
    #
    #
    # # 另一方面,__new__您必须自己创建实例。然后创建实例return
    # def __new__(cls):
    #     self = object.__new__(cls)
    #     print('__new__ :', str(id(self)))
    #     return self
    #
    #
    # # 在父类中调用方法时 super()要使用
    # class Cls(object):
    #     def __new__(cls):
    #         self = super().__new__(cls)
    #
    #
    # # super 是在执行多重继承时将父类的方法,调用为良好的Shioume的函数。
    # # 这一次不是多重继承, super().__new__(cls)因为object.__new__(cls)还有,是一样的。
    # # super()简写形式
    # class Cls(object):
    #     def __new__(cls):
    #         self = super(cls, cls).__new__(cls)
     
    """
    4、继承元组
    """
    
    # 1、 当元组继承时,不能初始化它,因为元组不能 以不变的方式进行改变
    # ImmutableRegion 一个代表矩形类,假设你希望此类不仅具有(x1 ,y1,x2,y2) 表示坐标,is_dot 表示标点,is_line 表示线,is_rectangle 表示属性
    # 假设它是您要预先定义的属性,而不是方法,因为您会经常引用它。
    # class ImmutableRegion(tuple):
    #     def __init__(self, args):
    #         x1 = self[0]
    #         y1 = self[1]
    #         x2 = self[2]
    #         y2 = self[3]
    #         width_0 = (x1 - x2 == 0)
    #         height_0 = (y1 - y2 == 0)
    #         is_rectangle = (not width_0 and not height_0)  # 0 0
    #         is_line = (width_0 != height_0)  # 0 1 or 1 0 xor
    #         is_dot = (width_0 and height_0)  # 1 1
    #         self[4] = is_rectangle  # <--- TypeError
    #         self[5] = is_line
    #         self[6] = is_dot
    #
    #
    # immutable_region = ImmutableRegion((2, 3, 3, 4))
    
    """
    运行结果
    这里的问题是元组是不可变的,因此您不能更改元素... __new__使用它
    Traceback (most recent call last):
      File "C:/Users/tangxx/Desktop/pojects/python设计模式/pyhon__new__方法.py", line 98, in <module>
        immutable_region = ImmutableRegion((2, 3, 3, 4))
      File "C:/Users/tangxx/Desktop/pojects/python设计模式/pyhon__new__方法.py", line 93, in __init__
        self[4] = is_rectangle  # <<<<<TypeError
    TypeError: 'ImmutableRegion' object does not support item assignment
    
    """
    
    
    # 用__new__初始化
    class ImmutableRegion(tuple):
        def __new__(cls, args):
            x1 = args[0]
            y1 = args[1]
            x2 = args[2]
            y2 = args[3]
            width_0 = (x1 - x2 == 0)
            hight_0 = (y1 - y2 == 0)
            is_rectangle = (not width_0 and not hight_0)
            is_line = (width_0 != hight_0)
            is_dot = (width_0 and hight_0)
    
            # super().__new__() # 同于下
            self = tuple.__new__(cls, (x1, y1, x2, y2, is_rectangle, is_line, is_dot ,))
            return self
    
    immutable_region = ImmutableRegion((2, 3, 3, 4))
    print(immutable_region)
    
    """
    运行结果
    (2, 3, 3, 4, True, False, False)
    
    """


    # 5.使用属性来引用属性。
    # 对话模式>>可以复制。
    class ImmutableRegion(tuple):
        def __new__(cls, args):
            x1 = args[0]
            y1 = args[1]
            x2 = args[2]
            y2 = args[3]
    
            width_0 = (x1 - x2 == 0)
            height_0 = (y1 - y2 == 0)
            is_rectangle = (not width_0 and not height_0)  # 0 0
            is_line = (width_0 != height_0)
            is_dot = (width_0 and height_0)
    
            # super().__new__(cls) # 同上
            self = tuple.__new__(cls, (x1, y1, x2, y2, is_rectangle, is_line, is_dot))
    
            return self
    
        def __repr__(self):
            x1, y1, x2, y2 = self.x1, self.y1, self.x2, self.y2
    
            return type.__name__ + f"{x1,y1,x2,y2}"
    
        x1=property(lambda self:self[0])
        y1=property(lambda self:self[1])
        x2=property(lambda self:self[2])
        y2=property(lambda self:self[3])
        is_rectangle=property(lambda self:self[4])
        is_line=property(lambda self:self[5])
        is_dot=property(lambda self:self[6])
    
    immitable_region=ImmutableRegion((2,3,3,4))
    
    print(immitable_region)
    print(immitable_region.is_rectangle)
    print(immitable_region.is_line)
    print(immitable_region.is_dot)
    
    """
    运行结果
    type(2, 3, 3, 4)
    True
    False
    False
    
    """
  • 相关阅读:
    js 复杂研究
    js 页面 保持状态 的方法
    C# 向上取整数
    js 获取dom 为null 测试
    net core 下 接受文件 测试
    layui 源码解读(部分)
    js 定时器
    js addEventListener
    C# 获得对象的命名空间 ?.
    修改maven的默认jdk版本
  • 原文地址:https://www.cnblogs.com/Xingtxx/p/12819404.html
Copyright © 2020-2023  润新知