📜  __new__ 在Python中

📅  最后修改于: 2022-05-13 01:55:02.680000             🧑  作者: Mango

__new__ 在Python中

Python是一种面向对象的编程语言,即Python中的一切都是对象。 Python中有一种特殊的方法,称为魔术方法或 dunder 方法(dunder 在这里的意思是“双下划线”)。 Python中的Dunder或magic方法是方法名称中具有两个前缀和后缀下划线的方法。这些通常用于运算符重载。
魔术方法的几个例子是: __init____add____len____repr__等。

注意:要了解有关魔术方法的更多信息,请单击此处。

__new__ 方法


每当实例化一个类时,都会调用__new____init__方法。 __new__方法将在创建对象时调用,并调用__init__方法来初始化对象。在基类object中,__new__ 方法被定义为需要传递参数cls的静态方法。 cls代表需要实例化的类,编译器在实例化的时候自动提供这个参数。

句法:

class class_name:
    def __new__(cls, *args, **kwargs):
        statements
        .
        .
        return super(class_name, cls).__new__(cls, *args, **kwargs)

注意:实例可以在__new__方法中创建,既可以使用super函数,也可以直接调用对象的__new__方法,如果父类是对象。即instance = super(MyClass, cls).__new__(cls, *args, **kwargs)instance = object.__new__(cls, *args, **kwargs)

如果类中同时存在 __init__ 方法和 __new__ 方法,则首先执行 __new__ 方法并决定是否使用 __init__ 方法,因为 __new__ 方法可以调用其他类的构造函数,也可以简单地将其他对象作为实例返回这节课。

例子:

# Python program to 
# demonstrate __new__
  
# don't forget the object specified as base
class A(object):
    def __new__(cls):
         print("Creating instance")
         return super(A, cls).__new__(cls)
  
    def __init__(self):
        print("Init is called")
  
A()

输出:

Creating instance
Init is called

上面的例子展示了调用类名时会自动调用 __new__ 方法,而 __new__ 方法每次返回类的实例时都会调用 __init__ 方法,将返回的实例作为self参数传递给 __init__,因此即使你是将实例保存在全局/静态某处并每次从 __new__ 返回它,然后每次执行此操作时都会调用 __init__。

这意味着如果 __new__ 方法省略了 super,__init__ 方法将不会被执行。让我们看看是不是这样。

# Python program to
# demonstrate __new__
  
class A(object):
    def __new__(cls):
        print("Creating instance")
  
    # It is not called
    def __init__(self):
        print("Init is called")
  
print(A())

输出:

Creating instance
None

在上面的例子中,可以看到__init__方法没有被调用并且实例化被评估为None因为构造函数没有返回任何东西。让我们看看如果 __new__ 和 __init__ 方法都返回了一些东西会发生什么。

# Python program to
# demonstrate __new__
  
class A(object):
    # new method returning a string
    def __new__(cls):
        print("Creating instance")
        return "GeeksforGeeks"
  
class B(object):
    # init method returning a string
    def __init__(self):
        print("Initializing instance")
        return "GeeksforGeeks"
  
print(A())
print(B())

输出:

Creating instance
GeeksforGeeks
Initializing instance
Traceback (most recent call last):
  File "/home/62216eb30d3856048eff916fb8d4c32d.py", line 17, in 
    print(B())
TypeError: __init__() should return None, not 'str'

这个 TypeError 是由调用 __init__ 方法的处理程序引发的,从 __init__ 方法返回任何东西都没有意义,因为它的目的只是改变新创建实例的新状态。

让我们尝试一个示例,其中 __new__ 方法返回不同类的实例。
例子:

# Python program to
# demonstrate __new__ method
  
# class whose object
# is returned
class GeeksforGeeks(object):
    def __str__(self):
        return "GeeksforGeeks"
          
# class returning object
# of different class
class Geek(object):
    def __new__(cls):
        return GeeksforGeeks()
          
    def __init__(self):
        print("Inside init")
          
print(Geek())

输出:

GeeksforGeeks