1 /*=============================================================================
2 Copyright (c) 2002-2003 Martin Wille
3 http://spirit.sourceforge.net/
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 #ifndef BOOST_SPIRIT_CONDITIONS_IPP
10 #define BOOST_SPIRIT_CONDITIONS_IPP
12 ///////////////////////////////////////////////////////////////////////////////
13 #include <boost/spirit/home/classic/meta/parser_traits.hpp>
14 #include <boost/spirit/home/classic/core/composite/epsilon.hpp>
16 ///////////////////////////////////////////////////////////////////////////////
17 namespace boost { namespace spirit {
19 BOOST_SPIRIT_CLASSIC_NAMESPACE_BEGIN
23 ///////////////////////////////////////////////////////////////////////////////
25 // condition evaluation
27 ///////////////////////////////////////////////////////////////////////////////
28 //////////////////////////////////
29 // condition_parser_selector, decides which parser to use for a condition
30 // If the template argument is a parser then that parser is used.
31 // If the template argument is a functor then a condition parser using
32 // the functor is chosen
34 template <typename T> struct embed_t_accessor
36 typedef typename T::embed_t type;
39 template <typename ConditionT>
40 struct condition_parser_selector
44 is_parser<ConditionT>,
46 condition_parser<ConditionT>
50 typedef typename embed_t_accessor<type>::type embed_t;
53 //////////////////////////////////
54 // condition_evaluator, uses a parser to check wether a condition is met
55 // takes a parser or a functor that can be evaluated in boolean context
56 // as template parameter.
58 // JDG 4-15-03 refactored
59 template <typename ConditionT>
60 struct condition_evaluator
62 typedef condition_parser_selector<ConditionT> selector_t;
63 typedef typename selector_t::type selected_t;
64 typedef typename selector_t::embed_t cond_embed_t;
66 typedef typename boost::call_traits<cond_embed_t>::param_type
69 condition_evaluator(param_t s) : cond(s) {}
71 /////////////////////////////
72 // evaluate, checks wether condition is met
73 // returns length of a match or a negative number for no-match
74 template <typename ScannerT>
76 evaluate(ScannerT const &scan) const
78 typedef typename ScannerT::iterator_t iterator_t;
79 typedef typename parser_result<selected_t, ScannerT>::type cres_t;
80 iterator_t save(scan.first);
81 cres_t result = cond.parse(scan);
82 if (!result) // reset the position if evaluation
83 scan.first = save; // fails.
84 return result.length();
90 ///////////////////////////////////////////////////////////////////////////////
93 BOOST_SPIRIT_CLASSIC_NAMESPACE_END
95 }} // namespace boost::spirit