classmethod作为构造函数和继承

Tou*_*uki 5 python inheritance constructor class-design

问题很简单.如果一个类B继承一个类A并想要覆盖一个用作构造函数的'classmethod'(我想你称之为"工厂方法").问题是B.classmethod需要重用A.classmethod,但是它必须创建类A的实例,而它是类A的子类 - 因为,作为类方法,它没有自我.然后,它似乎不是设计它的正确方法.

我做的例子很简单,我通过阅读numpy数组等做了更复杂的事情.但我想这里没有信息丢失.

class A:
    def __init__(self, a):
        self.el1 = a

    @classmethod
    def from_csv(cls, csv_file):
        a = read_csv(csv_file) 
        return cls(a)

    @classmethod
    def from_hdf5 ...

class B(A):
    def __init__(self, a, b)
        A.(self, a)
        self.el2 = b

    @classmethod
    def from_csv(cls, csv_file):
        A_ = A.from_csv(csv_file) #instance of A created in B(A)
        b = [a_*2 for a_ in A.el]
        return cls(A.el, b) 
Run Code Online (Sandbox Code Playgroud)

是否有一种pythonic方式来处理?

Blc*_*ght 1

一种简单的解决方案是让类B__init__方法为其参数设置默认值b。这将使工作在继承时进行cls(a)调用。A.from_csv如果使用默认值,该__init__方法可以计算一个要存储的值a(就像您B.from_csv现在所做的那样)。

class B(A):
    def __init__(self, a, b=None):
        super().__init__(a)   # use super(B, self).__init__(a) if you're in Python 2
        self.el2 = b if b is not None else [i*2 for i in a]

    # don't override from_csv, B.from_csv will already return a B instance!
Run Code Online (Sandbox Code Playgroud)