Line data Source code
1 : // Boost.Range library
2 : //
3 : // Copyright Neil Groves 2014. Use, modification and
4 : // distribution is subject to the Boost Software License, Version
5 : // 1.0. (See accompanying file LICENSE_1_0.txt or copy at
6 : // http://www.boost.org/LICENSE_1_0.txt)
7 : //
8 : // For more information, see http://www.boost.org/libs/range/
9 : //
10 : /**
11 : * Copyright Soramitsu Co., Ltd. All Rights Reserved.
12 : * SPDX-License-Identifier: Apache-2.0
13 : */
14 : #ifndef BOOST_RANGE_DETAIL_DEFAULT_CONSTRUCTIBLE_UNARY_FN_HPP_INCLUDED
15 : #define BOOST_RANGE_DETAIL_DEFAULT_CONSTRUCTIBLE_UNARY_FN_HPP_INCLUDED
16 :
17 : #include <utility>
18 :
19 : #include <boost/mpl/if.hpp>
20 : #include <boost/optional/optional.hpp>
21 : #include <boost/type_traits/has_trivial_constructor.hpp>
22 :
23 : namespace boost {
24 : namespace range_detail {
25 :
26 : template <typename F, typename R>
27 : class default_constructible_unary_fn_wrapper {
28 : public:
29 : typedef R result_type;
30 :
31 : default_constructible_unary_fn_wrapper() {}
32 : default_constructible_unary_fn_wrapper(const F &source)
33 1580 : : m_impl(source) {}
34 : default_constructible_unary_fn_wrapper(
35 : const default_constructible_unary_fn_wrapper &source)
36 47400 : : m_impl(source.m_impl) {}
37 : default_constructible_unary_fn_wrapper &operator=(
38 : const default_constructible_unary_fn_wrapper &source) {
39 : if (source.m_impl) {
40 : // Lambda are not copy/move assignable.
41 : m_impl.emplace(*source.m_impl);
42 : } else {
43 : m_impl.reset();
44 : }
45 : return *this;
46 : }
47 : template <typename Arg>
48 : R operator()(Arg &&arg) const {
49 1570 : BOOST_ASSERT(m_impl);
50 1570 : return (*m_impl)(std::forward<Arg>(arg));
51 0 : }
52 :
53 : private:
54 : boost::optional<F> m_impl;
55 : };
56 :
57 : template <typename F, typename R>
58 : struct default_constructible_unary_fn_gen {
59 : typedef typename boost::mpl::if_<
60 : boost::has_trivial_default_constructor<F>,
61 : F,
62 : default_constructible_unary_fn_wrapper<F, R> >::type type;
63 : };
64 :
65 : } // namespace range_detail
66 : } // namespace boost
67 :
68 : #endif // include guard
|