如何使用多个参数覆盖Python类的构造函数?

Ale*_*der 26 python constructor

说,我有一个类Foo,扩展类Bar.我想稍微改写Foo的指导者.而且我甚至不想知道Bar的构造函数是什么.有没有办法做到这一点?

如果你不明白,我的意思是:

class Bar:
   def __init__ (self, arg1=None, arg2=None, ... argN=None):
      ....


class Foo (Bar):
    #Here i just want add additional parameter to constructor, but don't want to know anything about Bar's other parameters (arg1, arg2..., argN)
    def __init__ (self, my_new_arg=None, ??? )
       self.new_arg = my_new_arg
       Bar.__init__(self, ??? )
Run Code Online (Sandbox Code Playgroud)

有没有办法把简短而优雅的东西放在??? 在这段代码?(可能是args/kwargs的一些变体)

Aco*_*orn 45

class Parent(object):
    def __init__(self, a, b):
        print 'a', a
        print 'b', b

class Child(Parent):
    def __init__(self, c, d, *args, **kwargs):
        print 'c', c
        print 'd', d
        super(Child, self).__init__(*args, **kwargs)

test = Child(1,2,3,4)
Run Code Online (Sandbox Code Playgroud)

输出:

c 1
d 2
a 3
b 4

  • @Mike'Pomax'Kamermans 你的意思可能是“super().__init__(*args, **kwargs)”? (2认同)

Ray*_*ger 11

*args, **kwds@Acorn提出的解决方案是一个良好的开端(尽管我对问题的*args部分内容有疑问).这篇文章在Python的Super Considered Super文章中进行了大量改进.

*args部分是不明智的,因为它不允许您在层次结构中插入新类,并且它阻止子类与可能具有不兼容的位置参数的其他类一起使用多重继承.该**kwds方法效果更好,因为它不强制执行调用链的特定排序.

另请注意,您可以使用命名参数从其他关键字参数中分离并删除当前方法的命名参数,然后再将其传递给链:

class Bar(object):
   def __init__(self, arg1=None, arg2=None, argN=None):
       print arg1, arg2, argN

class Foo(Bar):
    def __init__(self, my_new_arg=None, **kwds):
       super(Foo, self).__init__(**kwds)
       self.new_arg = my_new_arg
       print my_new_arg

f = Foo(my_new_arg='x', arg2='y')
Run Code Online (Sandbox Code Playgroud)

让每个方法剥离它所需的参数很重要,因为诸如object .__ init__之类的父方法根本不需要参数.

最后需要注意,如果你要使用超级,请确保您的最顶层的类是新型的(即它继承自对象或其它一些内置类型).