1 #ifndef BOOST_MP11_BIND_HPP_INCLUDED
2 #define BOOST_MP11_BIND_HPP_INCLUDED
4 // Copyright 2017, 2018 Peter Dimov.
6 // Distributed under the Boost Software License, Version 1.0.
8 // See accompanying file LICENSE_1_0.txt or copy at
9 // http://www.boost.org/LICENSE_1_0.txt
11 #include <boost/mp11/algorithm.hpp>
12 #include <boost/mp11/utility.hpp>
21 template<template<class...> class F, class... T> struct mp_bind_front
23 // the indirection through mp_defer works around the language inability
24 // to expand U... into a fixed parameter list of an alias template
26 template<class... U> using fn = typename mp_defer<F, T..., U...>::type;
29 template<class Q, class... T> using mp_bind_front_q = mp_bind_front<Q::template fn, T...>;
32 template<template<class...> class F, class... T> struct mp_bind_back
34 template<class... U> using fn = typename mp_defer<F, U..., T...>::type;
37 template<class Q, class... T> using mp_bind_back_q = mp_bind_back<Q::template fn, T...>;
40 template<std::size_t I> struct mp_arg
42 template<class... T> using fn = mp_at_c<mp_list<T...>, I>;
56 template<template<class...> class F, class... T> struct mp_bind;
61 template<class V, class... T> struct eval_bound_arg
66 template<std::size_t I, class... T> struct eval_bound_arg<mp_arg<I>, T...>
68 using type = typename mp_arg<I>::template fn<T...>;
71 template<template<class...> class F, class... U, class... T> struct eval_bound_arg<mp_bind<F, U...>, T...>
73 using type = typename mp_bind<F, U...>::template fn<T...>;
76 template<template<class...> class F, class... U, class... T> struct eval_bound_arg<mp_bind_front<F, U...>, T...>
78 using type = typename mp_bind_front<F, U...>::template fn<T...>;
81 template<template<class...> class F, class... U, class... T> struct eval_bound_arg<mp_bind_back<F, U...>, T...>
83 using type = typename mp_bind_back<F, U...>::template fn<T...>;
88 template<template<class...> class F, class... T> struct mp_bind
90 #if BOOST_MP11_WORKAROUND( BOOST_MP11_MSVC, == 1915 )
93 template<class... U> struct _f { using type = F<typename detail::eval_bound_arg<T, U...>::type...>; };
97 template<class... U> using fn = typename _f<U...>::type;
101 template<class... U> using fn = F<typename detail::eval_bound_arg<T, U...>::type...>;
106 template<class Q, class... T> using mp_bind_q = mp_bind<Q::template fn, T...>;
111 #endif // #ifndef BOOST_MP11_BIND_HPP_INCLUDED