In Python, how can I enforce a method's input and output invariants in child classes?

184 Views Asked by At

Is there a convenient way to enforce a method's input and output invariants, when the method is overridden in a subclass?

By enforcing invariants, I mean checking things like:

  • The number of input arguments
  • The types of some/all of the inputs
  • The number of output arguments
  • The types of some/all of the outputs

(Related questions have asked about enforcing the # of input arguments, but not the types. Others have asserted that explicit type checking is unpythonic, but, well, in this instance I don't care.)

For example, I have a base class B, with a method to be subclassed that takes an int and returns a float.

class B(object):
    def returns_float(self, int_arg):
        raise NotImplementedException("implement me")

To enforce this int->float signature, I currently split the method into returns_float(), and its implementation, _returns_float(). The subclass overrides the latter.

class B(object):
    def returns_float(self, int_arg):
        if not numpy.issubdtype(int_arg, 'int'):
            raise TypeError("Arg isn't an int.")

        result = self._returns_float(int_arg)

        if not numpy.issubdtype(result, 'float64'):
            raise TypeError("Return type isn't a float64")

        return result

    def _returns_float(self, int_arg):
        raise NotImplementedException("implement me")

This is flexible and explicit, but I'm wondering if there's some slicker way to do this?

0

There are 0 best solutions below