docs: def hyperrectangle(lower, upper, bdy=True):
      '''Returns the indicator function of a hyperrectangle.
  
      :param lower:
  
          Vector-like numpy array, defining the lower boundary of the hyperrectangle.\n
          len(lower) fixes the dimension.
  
      :param upper:
  
          Vector-like numpy array, defining the upper boundary of the hyperrectangle.\n
  
      :param bdy:
  
          Bool. When ``x`` is at the hyperrectangles's boundary then
          ``hr_indicator(x)`` returns ``True`` if and only if ``bdy=True``.
  
      '''
      # copy input
      lower = _np.array(lower)
      upper = _np.array(upper)
      dim = len(lower)
      if (upper <= lower).any():
          raise ValueError('invalid input; found upper <= lower')
  
      if bdy:
          def hr_indicator(x):
              if len(x) != dim:
                  raise ValueError('input has wrong dimension (%i instead of %i)' % (len(x), dim))
              if (lower <= x).all() and (x <= upper).all():
                  return True
              return False
      else:
          def hr_indicator(x):
              if len(x) != dim:
                  raise ValueError('input has wrong dimension (%i instead of %i)' % (len(x), dim))
              if (lower < x).all() and (x < upper).all():
                  return True
              return False
  
      # write docstring for ball_indicator
      hr_indicator.__doc__  = 'automatically generated hyperrectangle indicator function:'
      hr_indicator.__doc__ += '\nlower = ' + repr(lower)[6:-1]
      hr_indicator.__doc__ += '\nupper = ' + repr(upper)[6:-1]
      hr_indicator.__doc__ += '\nbdy   = ' + str(bdy)
  
      return hr_indicator