| 123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300 | #ifndef __GBLIBCPP_FUNCTIONAL__#define __GBLIBCPP_FUNCTIONAL__#include <bits/fwd_functional>#include <cstddef>#include <memory>#include <new>#include <utility>#include <type_traits>namespace std {template <typename Func, typename... Args>constexpr auto invoke(Func&& func, Args&&... args)    noexcept(std::is_nothrow_invocable_v<Func, Args...>)    -> std::enable_if_t<std::is_invocable_v<Func, Args...>,        std::invoke_result_t<Func, Args...>>{    return __helpers::INVOKE(std::forward<Func>(func), std::forward<Args>(args)...);}template <typename R, typename Func, typename... Args>constexpr auto invoke_r(Func&& func, Args&&... args)    noexcept(std::is_nothrow_invocable_r_v<R, Func, Args...>)    -> std::enable_if_t<std::is_invocable_r_v<R, Func, Args...>, R>{    return __helpers::INVOKE_R<R>(std::forward<Func>(func), std::forward<Args>(args)...);}namespace __helpers {template <typename T> constexpr void __reference_wrapper_check(T&) noexcept {}template <typename T> void __reference_wrapper_check(T&&) = delete;} // namespace __helperstemplate <typename T>class reference_wrapper {private:    T* _ptr;    template <typename Ref, typename =         decltype(__helpers::__reference_wrapper_check<T>(std::declval<Ref>()))>    struct __check_reference_valid        : public bool_constant<!std::is_same_v<reference_wrapper, std::decay_t<Ref>>> {};public:    using type = T;    constexpr T& get(void) const noexcept { return *_ptr; }    constexpr operator T&(void) const noexcept { return *_ptr; }    template <typename U, std::enable_if_t<__check_reference_valid<U>::value, bool> = true>    constexpr reference_wrapper(U&& ref)        noexcept(noexcept(__helpers::__reference_wrapper_check<T>(std::declval<U>())))        : _ptr(std::addressof(ref)) {}    constexpr reference_wrapper(const reference_wrapper& val) noexcept    {        _ptr = val._ptr;    }    constexpr reference_wrapper& operator=(const reference_wrapper& val) noexcept = default;    // TODO: std::invoke_result_t    template <typename... Args>    constexpr invoke_result_t<type&, Args...>    operator()(Args&&... args) const noexcept(is_nothrow_invocable_v<type&, Args...>)    {        return std::invoke(get(), std::forward<Args>(args)...);    }};template <typename T>reference_wrapper(T&) -> reference_wrapper<T>;namespace __inner {    template <typename Ret, typename... Args>    class _function_base {    public:        virtual constexpr ~_function_base() = default;        virtual constexpr Ret operator()(Args... args) const = 0;        virtual constexpr void copy_to(_function_base* func) = 0;        virtual constexpr void move_to(_function_base* func) = 0;        virtual explicit constexpr operator bool(void) const = 0;    };    template <typename FuncLike, typename Ret, typename... Args>    class _function : public _function_base<Ret, Args...> {    private:        using __enable = std::enable_if_t<            std::is_same_v<Ret,                decltype(std::declval<std::decay_t<FuncLike>>()(std::declval<Args>()...))>        >;        FuncLike func;    public:        constexpr _function(const FuncLike& _func) : func(_func) {}        constexpr _function(FuncLike&& _func) : func(std::move(_func)) {}        constexpr Ret operator()(Args... args) const override        {            return std::invoke(func, std::forward<Args>(args)...);        }        constexpr void copy_to(_function_base<Ret, Args...>* dst) override        {            new (reinterpret_cast<_function*>(dst)) _function(*this);        }        constexpr void move_to(_function_base<Ret, Args...>* dst) override        {            new (reinterpret_cast<_function*>(dst)) _function(std::move(*this));        }        constexpr explicit operator bool(void) const override        {            return true;        }    };    template <typename Ret, typename... Args>    class _function<nullptr_t, Ret, Args...> : public _function_base<Ret, Args...> {    public:        [[noreturn]] Ret operator()(Args...) const override        {            // TODO: exception            *((int*)(100^100)) = 1; // triggers access to null pointer            for (;;);        }        constexpr void copy_to(_function_base<Ret, Args...>* dst) override        {            new (reinterpret_cast<_function*>(dst)) _function(*this);        }        constexpr void move_to(_function_base<Ret, Args...>* dst) override        {            new (reinterpret_cast<_function*>(dst)) _function(std::move(*this));        }        constexpr explicit operator bool(void) const override        {            return false;        }    };} // namespace __innertemplate <typename Ret, typename... Args>class function<Ret(Args...)> {public:    using result_type = Ret;private:    char _data[sizeof(void*) * 2];    using fb_t = __inner::_function_base<Ret, Args...>;    constexpr fb_t* _f(void) const    {        return (fb_t*)_data;    }    constexpr void _clear(void)    {        _f()->~_function_base();    }public:    constexpr function() noexcept    {        new (_f()) __inner::_function<nullptr_t, Ret, Args...>();    }    constexpr function(nullptr_t) noexcept : function() {}    constexpr function(const function& func)    {        func._f()->copy_to(_f());    }    constexpr function(function&& func) noexcept    {        func._f()->move_to(_f());    }    template <typename FuncLike, std::enable_if_t        <            std::is_same_v<                Ret,                decltype(std::declval<std::decay_t<FuncLike>>()(std::declval<Args>()...))            >            && (sizeof(std::decay_t<FuncLike>) <= sizeof(_data))            && !std::is_same_v<std::decay_t<FuncLike>, function>        , bool> = true    >    constexpr function(FuncLike&& func)    {        new (_f()) __inner::_function<std::decay_t<FuncLike>, Ret, Args...>(std::forward<FuncLike>(func));    }    constexpr ~function()    {        _clear();    }    constexpr Ret operator()(Args... args) const    {        return (*_f())(std::forward<Args>(args)...);    }    explicit operator bool(void) const noexcept    {        return !!*_f();    }    function& operator=(function&& rhs)    {        _clear();        rhs._f()->move_to(_f());        return *this;    }    void swap(function& other) noexcept    {        function tmp(std::move(other));        other = std::move(*this);        *this = std::move(tmp);    }    function& operator=(const function& rhs)    {        _clear();        rhs._f()->copy_to(_f());        return *this;    }    function& operator=(nullptr_t) noexcept    {        _clear();        new (_f()) __inner::_function<nullptr_t, Ret, Args...>();        return *this;    }    template <typename FuncLike, std::enable_if_t        <            std::is_same_v<                Ret,                decltype(std::declval<std::decay_t<FuncLike>>()(std::declval<Args>()...))            >            && (sizeof(std::decay_t<FuncLike>) <= sizeof(_data))            && !std::is_same_v<std::decay_t<FuncLike>, function>        , bool> = true    >    function& operator=(FuncLike&& func)    {        function{std::forward<FuncLike>(func)}.swap(*this);        return *this;    }    template <typename FuncLike>    function& operator=(std::reference_wrapper<FuncLike> func) noexcept    {        function{func}.swap(*this);        return *this;    }};template <typename Ret, typename... Args>bool operator==(const std::function<Ret(Args...)>& func, std::nullptr_t) noexcept{    return !func;}template <typename Ret, typename... Args>void swap(std::function<Ret(Args...)>& lhs, std::function<Ret(Args...)>& rhs) noexcept{    return lhs.swap(rhs);}template <typename T>constexpr std::reference_wrapper<T> ref(T& t) noexcept{    return std::reference_wrapper<T>((t));}template <typename T>constexpr std::reference_wrapper<T>    ref(std::reference_wrapper<T> t) noexcept{    return t;}template <typename T>constexpr std::reference_wrapper<const T> cref(const T& t) noexcept{    return std::reference_wrapper<const T>((t));}template <typename T>constexpr std::reference_wrapper<const T>    cref(std::reference_wrapper<T> t) noexcept{    return t;}} // namespace std#endif
 |