Пример #1
0
    def decorator(implementation):
        if verify:
            verify_matching_signatures(implementation, dispatcher)

        if docs_from_dispatcher:
            add_docstring(implementation, dispatcher.__doc__)

        # Equivalently, we could define this function directly instead of using
        # exec. This version has the advantage of giving the helper function a
        # more interpettable name. Otherwise, the original function does not
        # show up at all in many cases, e.g., if it's written in C or if the
        # dispatcher gets an invalid keyword argument.
        source = _wrapped_func_source.format(name=implementation.__name__)

        source_object = compile(source,
                                filename='<__array_function__ internals>',
                                mode='exec')
        scope = {
            'implementation': implementation,
            'dispatcher': dispatcher,
            'functools': functools,
            'implement_array_function': implement_array_function,
        }
        exec(source_object, scope)

        public_api = scope[implementation.__name__]

        if module is not None:
            public_api.__module__ = module

        public_api._implementation = implementation

        return public_api
Пример #2
0
    def decorator(implementation):
        if verify:
            verify_matching_signatures(implementation, dispatcher)

        if docs_from_dispatcher:
            add_docstring(implementation, dispatcher.__doc__)

        @functools.wraps(implementation)
        def public_api(*args, **kwargs):
            relevant_args = dispatcher(*args, **kwargs)
            return implement_array_function(
                implementation, public_api, relevant_args, args, kwargs)

        if module is not None:
            public_api.__module__ = module

        return public_api
Пример #3
0
    def decorator(implementation):
        if verify:
            verify_matching_signatures(implementation, dispatcher)

        if docs_from_dispatcher:
            add_docstring(implementation, dispatcher.__doc__)

        @functools.wraps(implementation)
        def public_api(*args, **kwargs):
            try:
                relevant_args = dispatcher(*args, **kwargs)
            except TypeError as exc:
                # Try to clean up a signature related TypeError.  Such an
                # error will be something like:
                #     dispatcher.__name__() got an unexpected keyword argument
                #
                # So replace the dispatcher name in this case.  In principle
                # TypeErrors may be raised from _within_ the dispatcher, so
                # we check that the traceback contains a string that starts
                # with the name.  (In principle we could also check the
                # traceback length, as it would be deeper.)
                msg = exc.args[0]
                disp_name = dispatcher.__name__
                if not isinstance(msg, str) or not msg.startswith(disp_name):
                    raise

                # Replace with the correct name and re-raise:
                new_msg = msg.replace(disp_name, public_api.__name__)
                raise TypeError(new_msg) from None

            return implement_array_function(implementation, public_api,
                                            relevant_args, args, kwargs)

        public_api.__code__ = public_api.__code__.replace(
            co_name=implementation.__name__,
            co_filename='<__array_function__ internals>')
        if module is not None:
            public_api.__module__ = module

        public_api._implementation = implementation

        return public_api
Пример #4
0
    def decorator(implementation):
        if verify:
            verify_matching_signatures(implementation, dispatcher)

        if docs_from_dispatcher:
            add_docstring(implementation, dispatcher.__doc__)

        @functools.wraps(implementation)
        def public_api(*args, **kwargs):
            relevant_args = dispatcher(*args, **kwargs)
            return implement_array_function(implementation, public_api,
                                            relevant_args, args, kwargs)

        if module is not None:
            public_api.__module__ = module

        # TODO: remove this when we drop Python 2 support (functools.wraps)
        # adds __wrapped__ automatically in later versions)
        public_api.__wrapped__ = implementation

        return public_api
Пример #5
0
    def decorator(implementation):
        if verify:
            verify_matching_signatures(implementation, dispatcher)

        if docs_from_dispatcher:
            add_docstring(implementation, dispatcher.__doc__)

        @functools.wraps(implementation)
        def public_api(*args, **kwargs):
            relevant_args = dispatcher(*args, **kwargs)
            return implement_array_function(
                implementation, public_api, relevant_args, args, kwargs)

        if module is not None:
            public_api.__module__ = module

        # TODO: remove this when we drop Python 2 support (functools.wraps
        # adds __wrapped__ automatically in later versions)
        public_api.__wrapped__ = implementation

        return public_api
Пример #6
0
    def decorator(implementation):
        if verify:
            verify_matching_signatures(implementation, dispatcher)

        if docs_from_dispatcher:
            add_docstring(implementation, dispatcher.__doc__)

        @functools.wraps(implementation)
        def public_api(*args, **kwargs):
            relevant_args = dispatcher(*args, **kwargs)
            return implement_array_function(implementation, public_api,
                                            relevant_args, args, kwargs)

        public_api.__code__ = public_api.__code__.replace(
            co_name=implementation.__name__,
            co_filename='<__array_function__ internals>')
        if module is not None:
            public_api.__module__ = module

        public_api._implementation = implementation

        return public_api
Пример #7
0
    def decorator(implementation):
        if verify:
            verify_matching_signatures(implementation, dispatcher)

        if docs_from_dispatcher:
            add_docstring(implementation, dispatcher.__doc__)

        # Equivalently, we could define this function directly instead of using
        # exec. This version has the advantage of giving the helper function a
        # more interpettable name. Otherwise, the original function does not
        # show up at all in many cases, e.g., if it's written in C or if the
        # dispatcher gets an invalid keyword argument.
        source = textwrap.dedent("""
        @functools.wraps(implementation)
        def {name}(*args, **kwargs):
            relevant_args = dispatcher(*args, **kwargs)
            return implement_array_function(
                implementation, {name}, relevant_args, args, kwargs)
        """).format(name=implementation.__name__)

        source_object = compile(source,
                                filename="<__array_function__ internals>",
                                mode="exec")
        scope = {
            "implementation": implementation,
            "dispatcher": dispatcher,
            "functools": functools,
            "implement_array_function": implement_array_function,
        }
        exec(source_object, scope)

        public_api = scope[implementation.__name__]

        if module is not None:
            public_api.__module__ = module

        public_api._implementation = implementation

        return public_api
Пример #8
0
    def decorator(implementation):
        if verify:
            verify_matching_signatures(implementation, dispatcher)

        if docs_from_dispatcher:
            add_docstring(implementation, dispatcher.__doc__)

        # Equivalently, we could define this function directly instead of using
        # exec. This version has the advantage of giving the helper function a
        # more interpettable name. Otherwise, the original function does not
        # show up at all in many cases, e.g., if it's written in C or if the
        # dispatcher gets an invalid keyword argument.
        source = textwrap.dedent("""
        @functools.wraps(implementation)
        def {name}(*args, **kwargs):
            relevant_args = dispatcher(*args, **kwargs)
            return implement_array_function(
                implementation, {name}, relevant_args, args, kwargs)
        """).format(name=implementation.__name__)

        source_object = compile(
            source, filename='<__array_function__ internals>', mode='exec')
        scope = {
            'implementation': implementation,
            'dispatcher': dispatcher,
            'functools': functools,
            'implement_array_function': implement_array_function,
        }
        exec(source_object, scope)

        public_api = scope[implementation.__name__]

        if module is not None:
            public_api.__module__ = module

        return public_api
Пример #9
0
 def decorator(implementation):
     if docs_from_dispatcher:
         add_docstring(implementation, dispatcher.__doc__)
     if module is not None:
         implementation.__module__ = module
     return implementation
Пример #10
0
add_docstring(
    implement_array_function, """
    Implement a function with checks for __array_function__ overrides.

    All arguments are required, and can only be passed by position.

    Parameters
    ----------
    implementation : function
        Function that implements the operation on NumPy array without
        overrides when called like ``implementation(*args, **kwargs)``.
    public_api : function
        Function exposed by NumPy's public API originally called like
        ``public_api(*args, **kwargs)`` on which arguments are now being
        checked.
    relevant_args : iterable
        Iterable of arguments to check for __array_function__ methods.
    args : tuple
        Arbitrary positional arguments originally passed into ``public_api``.
    kwargs : dict
        Arbitrary keyword arguments originally passed into ``public_api``.

    Returns
    -------
    Result from calling ``implementation()`` or an ``__array_function__``
    method, as appropriate.

    Raises
    ------
    TypeError : if no implementation is found.
    """)
Пример #11
0
add_docstring(
    implement_array_function,
    """
    Implement a function with checks for __array_function__ overrides.

    All arguments are required, and can only be passed by position.

    Arguments
    ---------
    implementation : function
        Function that implements the operation on NumPy array without
        overrides when called like ``implementation(*args, **kwargs)``.
    public_api : function
        Function exposed by NumPy's public API originally called like
        ``public_api(*args, **kwargs)`` on which arguments are now being
        checked.
    relevant_args : iterable
        Iterable of arguments to check for __array_function__ methods.
    args : tuple
        Arbitrary positional arguments originally passed into ``public_api``.
    kwargs : dict
        Arbitrary keyword arguments originally passed into ``public_api``.

    Returns
    -------
    Result from calling ``implementation()`` or an ``__array_function__``
    method, as appropriate.

    Raises
    ------
    TypeError : if no implementation is found.
    """)
Пример #12
0
 def decorator(implementation):
     if module is not None:
         implementation.__module__ = module
     if docs_from_dispatcher:
         add_docstring(implementation, dispatcher.__doc__)
     return implementation