| /*============================================================================= |
| Copyright (c) 1998-2003 Joel de Guzman |
| http://spirit.sourceforge.net/ |
| |
| 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(BOOST_SPIRIT_SKIPPER_HPP) |
| #define BOOST_SPIRIT_SKIPPER_HPP |
| |
| /////////////////////////////////////////////////////////////////////////////// |
| #include <cctype> |
| |
| #include <boost/spirit/home/classic/namespace.hpp> |
| #include <boost/spirit/home/classic/core/scanner/scanner.hpp> |
| #include <boost/spirit/home/classic/core/primitives/impl/primitives.ipp> |
| |
| #include <boost/spirit/home/classic/core/scanner/skipper_fwd.hpp> |
| |
| namespace boost { namespace spirit { |
| |
| BOOST_SPIRIT_CLASSIC_NAMESPACE_BEGIN |
| |
| /////////////////////////////////////////////////////////////////////////// |
| // |
| // skipper_iteration_policy class |
| // |
| /////////////////////////////////////////////////////////////////////////// |
| template <typename BaseT> |
| struct skipper_iteration_policy : public BaseT |
| { |
| typedef BaseT base_t; |
| |
| skipper_iteration_policy() |
| : BaseT() {} |
| |
| template <typename PolicyT> |
| skipper_iteration_policy(PolicyT const& other) |
| : BaseT(other) {} |
| |
| template <typename ScannerT> |
| void |
| advance(ScannerT const& scan) const |
| { |
| BaseT::advance(scan); |
| scan.skip(scan); |
| } |
| |
| template <typename ScannerT> |
| bool |
| at_end(ScannerT const& scan) const |
| { |
| scan.skip(scan); |
| return BaseT::at_end(scan); |
| } |
| |
| template <typename ScannerT> |
| void |
| skip(ScannerT const& scan) const |
| { |
| while (!BaseT::at_end(scan) && impl::isspace_(BaseT::get(scan))) |
| BaseT::advance(scan); |
| } |
| }; |
| |
| /////////////////////////////////////////////////////////////////////////// |
| // |
| // no_skipper_iteration_policy class |
| // |
| /////////////////////////////////////////////////////////////////////////// |
| template <typename BaseT> |
| struct no_skipper_iteration_policy : public BaseT |
| { |
| typedef BaseT base_t; |
| |
| no_skipper_iteration_policy() |
| : BaseT() {} |
| |
| template <typename PolicyT> |
| no_skipper_iteration_policy(PolicyT const& other) |
| : BaseT(other) {} |
| |
| template <typename ScannerT> |
| void |
| skip(ScannerT const& /*scan*/) const {} |
| }; |
| |
| /////////////////////////////////////////////////////////////////////////// |
| // |
| // skip_parser_iteration_policy class |
| // |
| /////////////////////////////////////////////////////////////////////////// |
| namespace impl |
| { |
| template <typename ST, typename ScannerT, typename BaseT> |
| void |
| skipper_skip( |
| ST const& s, |
| ScannerT const& scan, |
| skipper_iteration_policy<BaseT> const&); |
| |
| template <typename ST, typename ScannerT, typename BaseT> |
| void |
| skipper_skip( |
| ST const& s, |
| ScannerT const& scan, |
| no_skipper_iteration_policy<BaseT> const&); |
| |
| template <typename ST, typename ScannerT> |
| void |
| skipper_skip( |
| ST const& s, |
| ScannerT const& scan, |
| iteration_policy const&); |
| } |
| |
| template <typename ParserT, typename BaseT> |
| class skip_parser_iteration_policy : public skipper_iteration_policy<BaseT> |
| { |
| public: |
| |
| typedef skipper_iteration_policy<BaseT> base_t; |
| |
| skip_parser_iteration_policy( |
| ParserT const& skip_parser, |
| base_t const& base = base_t()) |
| : base_t(base), subject(skip_parser) {} |
| |
| template <typename PolicyT> |
| skip_parser_iteration_policy(PolicyT const& other) |
| : base_t(other), subject(other.skipper()) {} |
| |
| template <typename ScannerT> |
| void |
| skip(ScannerT const& scan) const |
| { |
| impl::skipper_skip(subject, scan, scan); |
| } |
| |
| ParserT const& |
| skipper() const |
| { |
| return subject; |
| } |
| |
| private: |
| |
| ParserT const& subject; |
| }; |
| |
| /////////////////////////////////////////////////////////////////////////////// |
| // |
| // Free parse functions using the skippers |
| // |
| /////////////////////////////////////////////////////////////////////////////// |
| template <typename IteratorT, typename ParserT, typename SkipT> |
| parse_info<IteratorT> |
| parse( |
| IteratorT const& first, |
| IteratorT const& last, |
| parser<ParserT> const& p, |
| parser<SkipT> const& skip); |
| |
| /////////////////////////////////////////////////////////////////////////////// |
| // |
| // Parse function for null terminated strings using the skippers |
| // |
| /////////////////////////////////////////////////////////////////////////////// |
| template <typename CharT, typename ParserT, typename SkipT> |
| parse_info<CharT const*> |
| parse( |
| CharT const* str, |
| parser<ParserT> const& p, |
| parser<SkipT> const& skip); |
| |
| /////////////////////////////////////////////////////////////////////////////// |
| // |
| // phrase_scanner_t and wide_phrase_scanner_t |
| // |
| // The most common scanners. Use these typedefs when you need |
| // a scanner that skips white spaces. |
| // |
| /////////////////////////////////////////////////////////////////////////////// |
| typedef skipper_iteration_policy<> iter_policy_t; |
| typedef scanner_policies<iter_policy_t> scanner_policies_t; |
| typedef scanner<char const*, scanner_policies_t> phrase_scanner_t; |
| typedef scanner<wchar_t const*, scanner_policies_t> wide_phrase_scanner_t; |
| |
| /////////////////////////////////////////////////////////////////////////////// |
| |
| BOOST_SPIRIT_CLASSIC_NAMESPACE_END |
| |
| }} // namespace BOOST_SPIRIT_CLASSIC_NS |
| |
| #include <boost/spirit/home/classic/core/scanner/impl/skipper.ipp> |
| #endif |
| |