Python如何将__init__参数添加到子类

时间:2018-10-30 13:46:41

标签: python oop

我有一个共享基类的__ __的子类:

class SubClass(BaseClass)
    def __init__(self, param, *args, **kwargs):
        super().__init__(*args, **kwargs)
        self.thing = param

我一直遇到的问题是子类__初始化__参数“ param”被作为附加参数传递到super().__init__(*args, **kwargs)中。通常这会给我一个错误,例如:

TypeError: __init__() takes from 1 to 2 positional arguments but 3 were given

我不要那个。我只希望将“ param”用于这些子类实例。如何停止将额外的参数发送给基类__ __,而仍然可以在子类__ __中使用它呢?重现此问题的示例代码:

from unittest import TestCase


class TestCaseSubClass(TestCase):

    def __init__(self, param, *args, **kwargs):
        super().__init__(*args, **kwargs)  # Just use whatever is in TestCase's init + our stuff
        self.thing = param
        print(self.thing)


class TestClass(TestCaseSubClass(param='bdfbdfb')):

        def test_stuff(self):
            print('test stuff here')

或者只使用原始的python,没有导入,为什么我不能这样做? (相同的错误)

class A(object):
    def __init__(self, athing='thing'):
        self.thing = athing
        print(self.thing)

class AB(A):
    def __init__(self, param, *args, **kwargs):
        super().__init__(*args, **kwargs)
        self.param= param
        print(self.param)


class ABC(AB(param='thh')):
    pass

ABCinstance = ABC()

1 个答案:

答案 0 :(得分:1)

我将这个问题解释为“如何在不为其定义__init__的情况下为子类提供默认参数?”。一种可能的方法是将默认值定义为类属性,您可以在父类的__init__中访问该属性:

from unittest import TestCase

class TestCaseSubClass(TestCase):
    _default_param = None
    def __init__(self, *args, **kwargs):
        param = kwargs.pop("param", self._default_param)
        super().__init__(*args, **kwargs)  # Just use whatever is in TestCase's init + our stuff
        self.thing = param

class TestClass(TestCaseSubClass):
    _default_param = "bdfbdfb"
    def test_stuff(self):
        print('test stuff here')

x = TestClass()
print(x.thing) #"bdfbdfb"
y = TestClass(param="foo")
print(y.thing) #"foo"

此方法与您的问题中的参数格式不完全相同,因为现在param是仅关键字的参数,而不是命名的位置参数。实际的主要区别在于,除非您使用名称引用param,否则您不能为z = TestClass("foo")提供参数。例如,


基于对该问题的编辑和评论,另一种可能的解释可能是“如何通过某种必要的方法为子类提供一个传递给父类的参数?”,这对默认值没有要求。 。如果您愿意将param设置为强制参数,则只需在创建TestClass实例时将值传递进来即可。

from unittest import TestCase

class TestCaseSubClass(TestCase):
    def __init__(self, param, *args, **kwargs):
        super().__init__(*args, **kwargs)  # Just use whatever is in TestCase's init + our stuff
        self.thing = param

class TestClass(TestCaseSubClass):
    def test_stuff(self):
        print('test stuff here')

x = TestClass("bdfbdfb")
print(x.thing) #"bdfbdfb"