Warning: file_get_contents(/data/phpspider/zhask/data//catemap/2/python/361.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Python 调用子类函数以减少代码复制_Python_Class_Reduction - Fatal编程技术网

Python 调用子类函数以减少代码复制

Python 调用子类函数以减少代码复制,python,class,reduction,Python,Class,Reduction,我希望通过在父类中使用公共代码来减少子类中的代码复制,但仍然需要执行一些特定的处理,这些处理会根据子类的不同而变化。我知道从父母那里给孩子打电话是不好的。如何完成代码缩减?(或者我应该试一试吗?) 这是一个例子: class Address: def __init__(self, street, city, postal_code): self._street = street self._city = city self._posta

我希望通过在父类中使用公共代码来减少子类中的代码复制,但仍然需要执行一些特定的处理,这些处理会根据子类的不同而变化。我知道从父母那里给孩子打电话是不好的。如何完成代码缩减?(或者我应该试一试吗?)

这是一个例子:

class Address:

    def __init__(self, street, city, postal_code):

        self._street = street
        self._city = city
        self._postal_code = self.valid_postal_code(postal_code)

    def valid_postal_code(self, postal_code):
        """ Returns a validated postal code """
        #
        # A big bunch of code common to all postal codes
        #

        if child == Usa:
            return Usa.valid_postal_code(postal_code)
        else:
            return Canada.valid_postal_code(postal_code)    

class Usa(Address):

    def valid_postal_code(self, postal_code):
        """ Returns a validated US zip code """
        # Must be 5 digits or 5 digits plus dash 4 digits
        if len(postal_code) != 5 and len(postal_code) != 10:
            raise Exception("Bad postal code")

        return postal_code


class Canada(Address):

    def valid_postal_code(self, postal_code):
        """ Returns a validates Canadian postal code """
        # Must be A#A #A#
        if len(postal_code) == 6:
            postal_code = postal_code[0:3] + " " + postal_code[3:3]
        if len(postal_code) != 7:
            raise Exception("Bad postal code")

        return postal_code.upper()

每个重写方法都应该调用父方法

class Address:

    def __init__(self, street, city, postal_code):

        self._street = street
        self._city = city
        self._postal_code = self.valid_postal_code(postal_code)

    def valid_postal_code(self, postal_code):
        """ Returns a validated postal code """
        #
        # A big bunch of code common to all postal codes
        #
        ...


class Usa(Address):

    def valid_postal_code(self, postal_code):
        """ Returns a validated US zip code """

        # Must be 5 digits or 5 digits plus dash 4 digits
        if not super().valid_postal_code(postal_code) or len(postal_code) != 5 and len(postal_code) != 10:
            raise Exception("Bad postal code")

        return postal_code


class Canada(Address):

    def valid_postal_code(self, postal_code):
        """ Returns a validates Canadian postal code """
        # Must be A#A #A#
        if len(postal_code) == 6:
            postal_code = postal_code[0:3] + " " + postal_code[3:3]
        if not super().valid_postal_code() or len(postal_code) != 7:
            raise Exception("Bad postal code")

        return postal_code.upper()

有两种可能性:

  • 让父代码包含公共部分,子代码包含细节
    • 父级必须返回中间结果

  • 有两个父方法,其中一个是存根并由子方法重写
    • 父级将中间结果传递到存根中
第二种方法类似于:

class Address:

    def __init__(...):

    def valid_postal_code(self, postal_code):
        """ Returns a validated postal code """
        #
        # A big bunch of code common to all postal codes
        #
        return self._validate_postal_code(postal_code)

    def _validate_postal_code(self, postal_code):
        raise NotImplementedError


class Usa(Address):

    def _validate_postal_code(self, postal_code):
        """ Returns a validated US zip code """
        # Must be 5 digits or 5 digits plus dash 4 digits
        if len(postal_code) != 5 and len(postal_code) != 10:
            raise Exception("Bad postal code")
        return postal_code


class Canada(Address):

    def _validate_postal_code(self, postal_code):
        """ Returns a validates Canadian postal code """
        # Must be A#A #A#
        if len(postal_code) == 6:
            postal_code = postal_code[0:3] + " " + postal_code[3:3]
        if len(postal_code) != 7:
            raise Exception("Bad postal code")
        return postal_code.upper()

除了邮政编码之外,美国和加拿大的地址没有任何共同之处。基本上,
Address。有效的邮政编码
只有一个通用的占位符定义(如
pass
return True
return False
),每个子类都必须用一个适当的定义覆盖它。让所有邮政编码共有的一大串代码成为一个公共部分,但是子类中应该保留不同的验证逻辑每个子类应该通过
super()调用父类。有效的\u postal\u code()
而不是调用子实现的父类,因为父类不一定知道(或关心)哪些子类存在。