Correct type declaration of numpy types
Check e.g. in #278 : assume an input argument of a class or function is dtype: TYPE = np.float32. TYPE should not be np.dtype as the numpy types such as np.float32 are not an instance of it (isinstance(np.float32, np.dtype) = False and type(np.float32) = type). This contrasts with for instance PyTorch (isinstance(torch.float32, torch.dtype) = True) or TensorFlow (isinstance(tf.float32, tf.DType) = True). dtype: type = np.float32 is not very informative and exhaustive listing of all options also is far from ideal.
I believe the correct way is this (see https://github.com/SeldonIO/alibi/pull/506):
from typing import Type
def fun(dtype: Type[np.generic] = np.float32): ...
I.e. numpy scalar types like np.float32 are classes and there is a hierarchy with np.generic being the most general: https://numpy.org/doc/stable/reference/arrays.scalars.html. Using these classes as arguments means that they are of type Type and we can further constrain them to be subtypes of np.generic, thus the proposed Type[np.generic].