source: NonGTP/Boost/boost/spirit/fusion/algorithm/detail/find_if.ipp @ 857

Revision 857, 3.8 KB checked in by igarcia, 18 years ago (diff)
Line 
1/*=============================================================================
2    Copyright (c) 2003 Joel de Guzman
3    Copyright (c) 2004 Peder Holt
4
5    Use, modification and distribution is subject to the Boost Software
6    License, Version 1.0. (See accompanying file LICENSE_1_0.txt or copy at
7    http://www.boost.org/LICENSE_1_0.txt)
8==============================================================================*/
9#if !defined(FUSION_ALGORITHM_DETAIL_FIND_IF_HPP)
10#define FUSION_ALGORITHM_DETAIL_FIND_IF_HPP
11
12#include <boost/mpl/eval_if.hpp>
13#include <boost/mpl/apply.hpp>
14#include <boost/mpl/or.hpp>
15#include <boost/mpl/lambda.hpp>
16#include <boost/spirit/fusion/iterator/value_of.hpp>
17#include <boost/spirit/fusion/iterator/equal_to.hpp>
18#include <boost/spirit/fusion/iterator/next.hpp>
19
20namespace boost { namespace fusion { namespace detail
21{
22    template <typename Iterator, typename Pred>
23    struct apply_filter
24    {
25        typedef typename
26            mpl::apply1<
27                Pred
28              , typename meta::value_of<Iterator>::type
29            >::type
30        type;
31    };
32
33    template <typename First, typename Last, typename Pred>
34    struct main_find_if;
35
36    template <typename First, typename Last, typename Pred>
37    struct recursive_find_if
38    {
39        typedef typename
40            main_find_if<
41                typename meta::next<First>::type, Last, Pred
42            >::type
43        type;
44    };
45
46    template <typename First, typename Last, typename Pred>
47    struct main_find_if
48    {
49        typedef mpl::or_<
50            meta::equal_to<First, Last>
51          , apply_filter<First, Pred> >
52        filter;
53
54        typedef typename
55            mpl::eval_if<
56                filter
57              , mpl::identity<First>
58              , recursive_find_if<First, Last, Pred>
59            >::type
60        type;
61    };
62
63    template <typename First, typename Last, typename Pred>
64    struct static_find_if;
65
66    namespace static_find_if_detail {
67        template <typename First,typename Last,typename Pred,typename Iterator>
68        typename main_find_if<First,Last,typename mpl::lambda<Pred>::type>::type
69        call(static_find_if<First,Last,Pred> const& obj,Iterator const& iter);
70    }
71
72    template <typename First, typename Last, typename Pred>
73    struct static_find_if
74    {
75        typedef typename
76            main_find_if<
77                First
78              , Last
79              , typename mpl::lambda<Pred>::type
80            >::type
81        type;
82
83        //Workaround to please MSVC
84        template<typename Iterator>
85        static type
86        call(Iterator const& iter)
87        {
88            return static_find_if_detail::call(static_find_if<First,Last,Pred>(),iter);
89        }
90    };
91
92    namespace static_find_if_detail {
93        template <typename First,typename Last,typename Pred,typename Iterator>
94        typename static_find_if<First,Last,Pred>::type
95        call(static_find_if<First,Last,Pred> const&, Iterator const& iter, mpl::true_)
96        {
97            return iter;
98        };
99
100        template <typename First,typename Last,typename Pred,typename Iterator>
101        typename static_find_if<First,Last,Pred>::type
102        call(static_find_if<First,Last,Pred> const& obj,Iterator const& iter, mpl::false_)
103        {
104            return call(obj,fusion::next(iter));
105        };
106
107        template <typename First,typename Last,typename Pred,typename Iterator>
108        typename main_find_if<First,Last,typename mpl::lambda<Pred>::type>::type
109        call(static_find_if<First,Last,Pred> const& obj,Iterator const& iter)
110        {
111            typedef meta::equal_to<Iterator, BOOST_DEDUCED_TYPENAME static_find_if<First,Last,Pred>::type> found;
112            return call(obj,iter, found());
113        };       
114    }
115
116}}}
117
118#endif
Note: See TracBrowser for help on using the repository browser.