def test_type_alias(self):
        Pair = py_typing.Tuple[int, int]
        ListOfPairs = py_typing.List[Pair]

        pair_nb_type = types.Tuple((self.int_nb_type, self.int_nb_type))
        self.assertEqual(as_numba_type(Pair), pair_nb_type)
        self.assertEqual(as_numba_type(ListOfPairs),
                         types.ListType(pair_nb_type))
    def test_bad_union_throws(self):
        bad_unions = [
            py_typing.Union[str, int],
            py_typing.Union[int, type(None), py_typing.Tuple[bool, bool]],
        ]

        for bad_py_type in bad_unions:
            with self.assertRaises(TypingError) as raises:
                as_numba_type(bad_py_type)
            self.assertIn("Cannot type Union", str(raises.exception))
    def test_jitclass_registers(self):
        @jitclass
        class MyInt:
            x: int

            def __init__(self, value):
                self.x = value

        self.assertEqual(as_numba_type(MyInt), MyInt.class_type.instance_type)
 def test_nested_containers(self):
     IntList = py_typing.List[int]
     self.assertEqual(
         as_numba_type(py_typing.List[IntList]),
         types.ListType(types.ListType(self.int_nb_type)),
     )
     self.assertEqual(
         as_numba_type(py_typing.List[py_typing.Dict[float, bool]]),
         types.ListType(
             types.DictType(self.float_nb_type, self.bool_nb_type)),
     )
     self.assertEqual(
         as_numba_type(
             py_typing.Set[py_typing.Tuple[py_typing.Optional[int],
                                           float]]),
         types.Set(
             types.Tuple(
                 [types.Optional(self.int_nb_type), self.float_nb_type])),
     )
    def test_any_throws(self):
        Any = py_typing.Any

        any_types = [
            py_typing.Optional[Any],
            py_typing.List[Any],
            py_typing.Set[Any],
            py_typing.Dict[float, Any],
            py_typing.Dict[Any, float],
            py_typing.Tuple[int, Any],
        ]

        for bad_py_type in any_types:
            with self.assertRaises(TypingError) as raises:
                as_numba_type(bad_py_type)
            self.assertIn(
                "Cannot infer numba type of python type",
                str(raises.exception),
            )
    def test_optional(self):
        self.assertEqual(
            as_numba_type(py_typing.Optional[float]),
            types.Optional(self.float_nb_type),
        )
        self.assertEqual(
            as_numba_type(py_typing.Union[str, None]),
            types.Optional(self.str_nb_type),
        )
        self.assertEqual(
            as_numba_type(py_typing.Union[None, bool]),
            types.Optional(self.bool_nb_type),
        )

        # Optional[x] is a special case of Union[x, None].  We raise a
        # TypingError if the right type is not NoneType.
        with self.assertRaises(TypingError) as raises:
            as_numba_type(py_typing.Union[int, float])
        self.assertIn("Cannot type Union that is not an Optional",
                      str(raises.exception))
    def test_numba_types(self):
        numba_types = [
            types.intp,
            types.boolean,
            types.ListType(types.float64),
            types.DictType(types.intp,
                           types.Tuple([types.float32, types.float32])),
        ]

        for ty in numba_types:
            self.assertEqual(as_numba_type(ty), ty)
 def test_single_containers(self):
     self.assertEqual(
         as_numba_type(py_typing.List[float]),
         types.ListType(self.float_nb_type),
     )
     self.assertEqual(
         as_numba_type(py_typing.Dict[float, str]),
         types.DictType(self.float_nb_type, self.str_nb_type),
     )
     self.assertEqual(
         as_numba_type(py_typing.Set[complex]),
         types.Set(self.complex_nb_type),
     )
     self.assertEqual(
         as_numba_type(py_typing.Tuple[float, float]),
         types.Tuple([self.float_nb_type, self.float_nb_type]),
     )
     self.assertEqual(
         as_numba_type(py_typing.Tuple[float, complex]),
         types.Tuple([self.float_nb_type, self.complex_nb_type]),
     )
 def test_simple_types(self):
     self.assertEqual(as_numba_type(int), self.int_nb_type)
     self.assertEqual(as_numba_type(float), self.float_nb_type)
     self.assertEqual(as_numba_type(complex), self.complex_nb_type)
     self.assertEqual(as_numba_type(str), self.str_nb_type)
     self.assertEqual(as_numba_type(bool), self.bool_nb_type)
     self.assertEqual(as_numba_type(type(None)), self.none_nb_type)
Пример #10
0
def ol_isinstance(var, typs):
    def true_impl(var, typs):
        return True

    def false_impl(var, typs):
        return False

    var_ty = as_numba_type(var)

    if isinstance(var_ty, types.Optional):
        msg = f'isinstance cannot handle optional types. Found: "{var_ty}"'
        raise NumbaTypeError(msg)

    # NOTE: The current implementation of `isinstance` restricts the type of the
    # instance variable to types that are well known and in common use. The
    # danger of unrestricted tyoe comparison is that a "default" of `False` is
    # required and this means that if there is a bug in the logic of the
    # comparison tree `isinstance` returns False! It's therefore safer to just
    # reject the compilation as untypable!
    supported_var_ty = (types.Number, types.Bytes, types.RangeType,
                        types.DictType, types.LiteralStrKeyDict, types.List,
                        types.ListType, types.Tuple, types.UniTuple, types.Set,
                        types.Function, types.ClassType, types.UnicodeType,
                        types.ClassInstanceType, types.NoneType, types.Array)
    if not isinstance(var_ty, supported_var_ty):
        msg = f'isinstance() does not support variables of type "{var_ty}".'
        raise NumbaTypeError(msg)

    # Warn about the experimental nature of this feature.
    msg = "Use of isinstance() detected. This is an experimental feature."
    warnings.warn(msg, category=NumbaExperimentalFeatureWarning)

    t_typs = typs

    # Check the types that the var can be an instance of, it'll be a scalar,
    # a unituple or a tuple.
    if isinstance(t_typs, types.UniTuple):
        # corner case - all types in isinstance are the same
        t_typs = (t_typs.key[0])

    if not isinstance(t_typs, types.Tuple):
        t_typs = (t_typs, )

    for typ in t_typs:

        if isinstance(typ, types.Function):
            key = typ.key[0]  # functions like int(..), float(..), str(..)
        elif isinstance(typ, types.ClassType):
            key = typ  # jitclasses
        else:
            key = typ.key

        # corner cases for bytes, range, ...
        # avoid registering those types on `as_numba_type`
        types_not_registered = {
            bytes: types.Bytes,
            range: types.RangeType,
            dict: (types.DictType, types.LiteralStrKeyDict),
            list: types.List,
            tuple: types.BaseTuple,
            set: types.Set,
        }
        if key in types_not_registered:
            if isinstance(var_ty, types_not_registered[key]):
                return true_impl
            continue

        if isinstance(typ, types.TypeRef):
            # Use of Numba type classes is in general not supported as they do
            # not work when the jit is disabled.
            if key not in (types.ListType, types.DictType):
                msg = ("Numba type classes (except numba.typed.* container "
                       "types) are not supported.")
                raise NumbaTypeError(msg)
            # Case for TypeRef (i.e. isinstance(var, typed.List))
            #      var_ty == ListType[int64] (instance)
            #         typ == types.ListType  (class)
            return true_impl if type(var_ty) is key else false_impl
        else:
            numba_typ = as_numba_type(key)
            if var_ty == numba_typ:
                return true_impl
            elif isinstance(numba_typ, types.ClassType) and \
                    isinstance(var_ty, types.ClassInstanceType) and \
                    var_ty.key == numba_typ.instance_type.key:
                # check for jitclasses
                return true_impl
            elif isinstance(numba_typ, types.Container) and \
                    numba_typ.key[0] == types.undefined:
                # check for containers (list, tuple, set, ...)
                if isinstance(var_ty, numba_typ.__class__) or \
                    (isinstance(var_ty, types.BaseTuple) and \
                        isinstance(numba_typ, types.BaseTuple)):
                    return true_impl

    return false_impl
Пример #11
0
def register_class_type(cls, spec, class_ctor, builder):
    """
    Internal function to create a jitclass.

    Args
    ----
    cls: the original class object (used as the prototype)
    spec: the structural specification contains the field types.
    class_ctor: the numba type to represent the jitclass
    builder: the internal jitclass builder
    """
    # Normalize spec
    if spec is None:
        spec = OrderedDict()
    elif isinstance(spec, Sequence):
        spec = OrderedDict(spec)

    # Extend spec with class annotations.
    for attr, py_type in pt.get_type_hints(cls).items():
        if attr not in spec:
            spec[attr] = as_numba_type(py_type)

    _validate_spec(spec)

    # Fix up private attribute names
    spec = _fix_up_private_attr(cls.__name__, spec)

    # Copy methods from base classes
    clsdct = {}
    for basecls in reversed(inspect.getmro(cls)):
        clsdct.update(basecls.__dict__)

    methods, props, static_methods, others = {}, {}, {}, {}
    for k, v in clsdct.items():
        if isinstance(v, pytypes.FunctionType):
            methods[k] = v
        elif isinstance(v, property):
            props[k] = v
        elif isinstance(v, staticmethod):
            static_methods[k] = v
        else:
            others[k] = v

    # Check for name shadowing
    shadowed = (set(methods) | set(props) | set(static_methods)) & set(spec)
    if shadowed:
        raise NameError("name shadowing: {0}".format(', '.join(shadowed)))

    docstring = others.pop('__doc__', "")
    _drop_ignored_attrs(others)
    if others:
        msg = "class members are not yet supported: {0}"
        members = ', '.join(others.keys())
        raise TypeError(msg.format(members))

    for k, v in props.items():
        if v.fdel is not None:
            raise TypeError("deleter is not supported: {0}".format(k))

    jit_methods = {k: njit(v) for k, v in methods.items()}

    jit_props = {}
    for k, v in props.items():
        dct = {}
        if v.fget:
            dct['get'] = njit(v.fget)
        if v.fset:
            dct['set'] = njit(v.fset)
        jit_props[k] = dct

    jit_static_methods = {
        k: njit(v.__func__)
        for k, v in static_methods.items()
    }

    # Instantiate class type
    class_type = class_ctor(cls, ConstructorTemplate, spec, jit_methods,
                            jit_props, jit_static_methods)

    jit_class_dct = dict(class_type=class_type, __doc__=docstring)
    jit_class_dct.update(jit_static_methods)
    cls = JitClassType(cls.__name__, (cls, ), jit_class_dct)

    # Register resolution of the class object
    typingctx = cpu_target.typing_context
    typingctx.insert_global(cls, class_type)

    # Register class
    targetctx = cpu_target.target_context
    builder(class_type, typingctx, targetctx).register()
    as_numba_type.register(cls, class_type.instance_type)

    return cls
Пример #12
0
 def test_overwrite_type(self):
     as_numba_type = AsNumbaTypeRegistry()
     self.assertEqual(as_numba_type(float), self.float_nb_type)
     as_numba_type.register(float, types.float32)
     self.assertEqual(as_numba_type(float), types.float32)
     self.assertNotEqual(as_numba_type(float), self.float_nb_type)