source: NonGTP/Boost/boost/spirit/core/scanner/impl/skipper.ipp @ 857

Revision 857, 6.0 KB checked in by igarcia, 18 years ago (diff)
Line 
1/*=============================================================================
2    Copyright (c) 1998-2003 Joel de Guzman
3    http://spirit.sourceforge.net/
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(BOOST_SPIRIT_SKIPPER_IPP)
10#define BOOST_SPIRIT_SKIPPER_IPP
11
12///////////////////////////////////////////////////////////////////////////////
13namespace boost { namespace spirit {
14
15    struct space_parser;
16    template <typename BaseT>
17    struct no_skipper_iteration_policy;
18
19    namespace impl
20    {
21        template <typename ST, typename ScannerT, typename BaseT>
22        inline void
23        skipper_skip(
24            ST const& s,
25            ScannerT const& scan,
26            skipper_iteration_policy<BaseT> const&)
27        {
28            typedef scanner_policies<
29                no_skipper_iteration_policy<
30                    BOOST_DEDUCED_TYPENAME ScannerT::iteration_policy_t>,
31                BOOST_DEDUCED_TYPENAME ScannerT::match_policy_t,
32                BOOST_DEDUCED_TYPENAME ScannerT::action_policy_t
33            > policies_t;
34
35            scanner<BOOST_DEDUCED_TYPENAME ScannerT::iterator_t, policies_t>
36                scan2(scan.first, scan.last, policies_t(scan));
37            typedef typename ScannerT::iterator_t iterator_t;
38
39            for (;;)
40            {
41                iterator_t save = scan.first;
42                if (!s.parse(scan2))
43                {
44                    scan.first = save;
45                    break;
46                }
47            }
48        }
49
50        template <typename ST, typename ScannerT, typename BaseT>
51        inline void
52        skipper_skip(
53            ST const& s,
54            ScannerT const& scan,
55            no_skipper_iteration_policy<BaseT> const&)
56        {
57            for (;;)
58            {
59                typedef typename ScannerT::iterator_t iterator_t;
60                iterator_t save = scan.first;
61                if (!s.parse(scan))
62                {
63                    scan.first = save;
64                    break;
65                }
66            }
67        }
68
69        template <typename ST, typename ScannerT>
70        inline void
71        skipper_skip(
72            ST const& s,
73            ScannerT const& scan,
74            iteration_policy const&)
75        {
76            for (;;)
77            {
78                typedef typename ScannerT::iterator_t iterator_t;
79                iterator_t save = scan.first;
80                if (!s.parse(scan))
81                {
82                    scan.first = save;
83                    break;
84                }
85            }
86        }
87
88        template <typename SkipT>
89        struct phrase_parser
90        {
91            template <typename IteratorT, typename ParserT>
92            static parse_info<IteratorT>
93            parse(
94                IteratorT const&    first_,
95                IteratorT const&    last,
96                ParserT const&      p,
97                SkipT const&        skip)
98            {
99                typedef skip_parser_iteration_policy<SkipT> iter_policy_t;
100                typedef scanner_policies<iter_policy_t> scanner_policies_t;
101                typedef scanner<IteratorT, scanner_policies_t> scanner_t;
102
103                iter_policy_t iter_policy(skip);
104                scanner_policies_t policies(iter_policy);
105                IteratorT first = first_;
106                scanner_t scan(first, last, policies);
107                match<nil_t> hit = p.parse(scan);
108                scan.skip(scan);
109                return parse_info<IteratorT>(
110                    first, hit, hit && (first == last),
111                    hit.length());
112            }
113        };
114
115        template <>
116        struct phrase_parser<space_parser>
117        {
118            template <typename IteratorT, typename ParserT>
119            static parse_info<IteratorT>
120            parse(
121                IteratorT const&    first_,
122                IteratorT const&    last,
123                ParserT const&      p,
124                space_parser const&)
125            {
126                typedef skipper_iteration_policy<> iter_policy_t;
127                typedef scanner_policies<iter_policy_t> scanner_policies_t;
128                typedef scanner<IteratorT, scanner_policies_t> scanner_t;
129
130                IteratorT first = first_;
131                scanner_t scan(first, last);
132                match<nil_t> hit = p.parse(scan);
133                scan.skip(scan);
134                return parse_info<IteratorT>(
135                    first, hit, hit && (first == last),
136                    hit.length());
137            }
138        };
139    }
140
141    ///////////////////////////////////////////////////////////////////////////
142    //
143    //  Free parse functions using the skippers
144    //
145    ///////////////////////////////////////////////////////////////////////////
146    template <typename IteratorT, typename ParserT, typename SkipT>
147    inline parse_info<IteratorT>
148    parse(
149        IteratorT const&        first,
150        IteratorT const&        last,
151        parser<ParserT> const&  p,
152        parser<SkipT> const&    skip)
153    {
154        return impl::phrase_parser<SkipT>::
155            parse(first, last, p.derived(), skip.derived());
156    }
157   
158    ///////////////////////////////////////////////////////////////////////////
159    //
160    //  Parse function for null terminated strings using the skippers
161    //
162    ///////////////////////////////////////////////////////////////////////////
163    template <typename CharT, typename ParserT, typename SkipT>
164    inline parse_info<CharT const*>
165    parse(
166        CharT const*            str,
167        parser<ParserT> const&  p,
168        parser<SkipT> const&    skip)
169    {
170        CharT const* last = str;
171        while (*last)
172            last++;
173        return parse(str, last, p, skip);
174    }
175
176}} // namespace boost::spirit
177
178#endif
179
Note: See TracBrowser for help on using the repository browser.