第8.6节 Python类中的__new__方法深入剖析:调用父类__new__方法参数的困惑

知识共享许可协议 版权声明:署名,允许他人基于本文进行创作,且必须基于与原先许可协议相同的许可协议分发本文 (Creative Commons

上节《第8.5节 Python类中的__new__方法和构造方法__init__关系深入剖析:执行顺序及参数关系案例详解》通过案例详细分析了两个方法的执行顺序,不知大家是否注意到了,在上述代码中__new__方法调用父类的__new__方法时,传递参数只传递了cls一个实参,而没有传递后面两类参数(在本例中只有第一类参数中有1个实参10)。这个问题也困扰了老猿,我们先验证一下,如果传递全部参数会怎样。
一、 案例1:调用object类的__new__传参验证

  1. 我们将上节的类中的__new__方法改成传递全部参数后,类定义如下:
class Cir():
   def __new__(cls,*args,**kwargs):
       print("Python传递给__new__的参数:\n***cls: ",cls,"\n***args: ",args,"\n***kwargs:",kwargs)
       inst = super().__new__(cls,*args,**kwargs)  #将所有参数都传递进去
       print("__new__返回值:",inst)
       return inst

   def __init__(self,radius):
       print("In init,self的值为:",self,", radius的值为:",radius)
       self.radius = radius
  1. 定义实例变量:
cir=Cir(10)
执行结果报错:TypeError: object.__new__() takes no arguments
  1. 完整执行截屏如下: 在这里插入图片描述
  2. 案例分析:
    本案例定义的类没有自定义父类,因此其父类就是object,调用super().__new__方法执行的就是object类的__new__方法。结合上节正常执行执行的情况说明,不能传递所有参数,只能传递类名给object. __new__方法才能通过Python检查。
  1. 我们来看看Python的相关帮助文档
执行help(object.__new__),输出内容:
Help on built-in function __new__:

__new__(*args, **kwargs) method of builtins.type instance
    Create and return a new object.  See help(type) for accurate signature.

截图如下:
在这里插入图片描述
从上面没有看出object. __new__只能传入一个参数。

  1. 我们再到Python3.73文档中查一下:
    中文版:
    在这里插入图片描述

英文版:
在这里插入图片描述
从上面也说明是可以传多个值的。所以老猿没有明白这个地方实际使用时为什么不能传递多个值,如果哪位大拿研究清楚了欢迎给老猿指导。

二、 案例2:调用自定义父类的__new__传参验证

  1. 案例说明
    定义两个类,Vehicle类和Car类,Car是从Vehicle派生的,Car重写了__new__方法,验证几种情况:
  1. Vehicle类没有重写__ new__方法;
  2. Vehicle类重写__ new__方法,只传入cls;
  3. Vehicle类重写__ new__方法,传入所有参数。
  1. 案例代码:
  1. Vehicle类没有重写__ new__方法,Car重写该方法并调用父类传递所有参数,执行截屏如下:
    在这里插入图片描述
    说明还是不行,老猿认为这是因为Vehicle没有重写__ new__方法,就会调用其直接父类object的__ new__方法,导致不行。
  2. Vehicle类和Car类都重写__ new__方法,Car类调用父类的该方法时传递所有参数,而Vehicle类调用父类的该方法时只传cls参数,执行截屏如下:
    在这里插入图片描述
    可以看到执行成功。
  3. 还有一种情况,就是Vehicle类调用父类的该方法时传递所有参数,结果还是报错,在此就不提供截图了

三、 结论
通过以上案例验证,可以确认:

  1. 调用object. __ new__方法时,只能穿cls参数,否则会报错;
  2. 调用自定义类的自定义父类__ new__方法,可以传所有参数,要看父类的__ new__方法定义的参数是怎么定义的。

老猿Python(https://blog.csdn.net/LaoYuanPython)系列文章用于逐步介绍老猿学习Python后总结的学习经验,这些经验有助于没有接触过Python的程序员可以很容易地进入Python的世界。
欢迎大家批评指正,谢谢大家关注!

猜你喜欢

转载自blog.csdn.net/LaoYuanPython/article/details/93642448