/*============================================================================= Copyright (c) 2001-2011 Joel de Guzman Copyright (c) 2007 Dan Marsden Copyright (c) 2009 Christopher Schmidt Copyright (c) 2018 Kohei Takahashi Distributed under the Boost Software License, Version 1.0. (See accompanying file LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt) ==============================================================================*/ #if !defined(FUSION_FIND_IF_05052005_1107) #define FUSION_FIND_IF_05052005_1107 #include #include #include #include #include #include #include #include #include #include #include #include #include namespace boost { namespace fusion { namespace detail { template struct apply_filter { typedef typename mpl::apply1< Pred, Iterator>::type type; BOOST_STATIC_CONSTANT(int, value = type::value); }; template struct main_find_if; template struct recursive_find_if { typedef typename main_find_if< typename result_of::next::type, Last, Pred >::type type; }; template struct main_find_if { typedef mpl::or_< result_of::equal_to , apply_filter > filter; typedef typename mpl::eval_if< filter , mpl::identity , recursive_find_if >::type type; }; template< typename First, typename Last, typename Pred, bool> struct choose_find_if; template struct choose_find_if : main_find_if {}; template struct unroll_again; template struct apply_offset_filter { typedef typename result_of::advance_c::type Shifted; typedef typename mpl::apply1< Pred , Shifted >::type type; BOOST_STATIC_CONSTANT(int, value = type::value); }; template struct unrolled_find_if { typedef typename mpl::eval_if< apply_filter, mpl::identity, mpl::eval_if< apply_offset_filter, result_of::advance_c, mpl::eval_if< apply_offset_filter, result_of::advance_c, mpl::eval_if< apply_offset_filter, result_of::advance_c, unroll_again< Iter, Pred, n, 4> > > > >::type type; }; template struct unrolled_find_if { typedef typename mpl::eval_if< apply_filter, mpl::identity, mpl::eval_if< apply_offset_filter, result_of::advance_c, mpl::eval_if< apply_offset_filter, result_of::advance_c, result_of::advance_c > > >::type type; }; template struct unrolled_find_if { typedef typename mpl::eval_if< apply_filter, mpl::identity, mpl::eval_if< apply_offset_filter, result_of::advance_c, result_of::advance_c > >::type type; }; template struct unrolled_find_if { typedef typename mpl::eval_if< apply_filter, mpl::identity, result_of::advance_c >::type type; }; template struct unroll_again { typedef typename unrolled_find_if< typename result_of::advance_c::type, Pred, n-unrolling>::type type; }; template struct unrolled_find_if { typedef Iter type; }; template struct choose_find_if { typedef typename result_of::distance::type N; typedef typename unrolled_find_if::type type; }; template struct static_find_if { typedef typename choose_find_if< First , Last , Pred , traits::is_random_access::value >::type type; template BOOST_CONSTEXPR BOOST_FUSION_GPU_ENABLED static type recursive_call(Iterator const& iter, mpl::true_) { return iter; } template BOOST_CONSTEXPR BOOST_FUSION_GPU_ENABLED static type recursive_call(Iterator const& iter, mpl::false_) { return recursive_call(fusion::next(iter)); } template BOOST_CONSTEXPR BOOST_FUSION_GPU_ENABLED static type recursive_call(Iterator const& iter) { typedef result_of::equal_to found; return recursive_call(iter, found()); } template BOOST_CONSTEXPR BOOST_FUSION_GPU_ENABLED static typename boost::disable_if, type>::type iter_call(Iterator const& iter) { return recursive_call(iter); } template BOOST_CONSTEXPR BOOST_FUSION_GPU_ENABLED static typename boost::enable_if, type>::type iter_call(Iterator const& iter) { typedef typename result_of::distance::type N; return fusion::advance(iter); } template BOOST_CONSTEXPR BOOST_FUSION_GPU_ENABLED static type call(Sequence& seq) { return iter_call(fusion::begin(seq)); } }; template struct result_of_find_if { typedef static_find_if< typename result_of::begin::type , typename result_of::end::type , Pred > filter; typedef typename filter::type type; }; }}} #endif