Boost logo

Boost-Commit :

Subject: [Boost-commit] svn:boost r60260 - trunk/libs/spirit/example/qi/scheme
From: joel_at_[hidden]
Date: 2010-03-06 20:28:23


Author: djowel
Date: 2010-03-06 20:28:23 EST (Sat, 06 Mar 2010)
New Revision: 60260
URL: http://svn.boost.org/trac/boost/changeset/60260

Log:
s-expressions first shot (with proper unicode handling).
Added:
   trunk/libs/spirit/example/qi/scheme/
   trunk/libs/spirit/example/qi/scheme/sexpr.cpp (contents, props changed)
   trunk/libs/spirit/example/qi/scheme/sexpr.hpp (contents, props changed)

Added: trunk/libs/spirit/example/qi/scheme/sexpr.cpp
==============================================================================
--- (empty file)
+++ trunk/libs/spirit/example/qi/scheme/sexpr.cpp 2010-03-06 20:28:23 EST (Sat, 06 Mar 2010)
@@ -0,0 +1,28 @@
+/*=============================================================================
+ Copyright (c) 2001-2010 Joel de Guzman
+
+ 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)
+=============================================================================*/
+#include "sexpr.hpp"
+
+int main()
+{
+ using namespace boost::spirit;
+ using namespace boost::spirit::qi;
+
+ char const* first = "\"this is a\\n hmmm... \\u20AC string\"";
+ char const* last = first + std::strlen(first);
+
+ scheme::string<char const*> p;
+
+ std::string result;
+ if (parse(first, last, p, result))
+ std::cout << "success: '" << result << '\'' << std::endl;
+ else
+ std::cout << "parse error" << std::endl;
+
+ return 0;
+}
+
+

Added: trunk/libs/spirit/example/qi/scheme/sexpr.hpp
==============================================================================
--- (empty file)
+++ trunk/libs/spirit/example/qi/scheme/sexpr.hpp 2010-03-06 20:28:23 EST (Sat, 06 Mar 2010)
@@ -0,0 +1,118 @@
+/*=============================================================================
+ Copyright (c) 2001-2010 Joel de Guzman
+
+ 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_SEXPR)
+#define BOOST_SPIRIT_SEXPR
+
+#include <string>
+
+#define BOOST_SPIRIT_UNICODE // We'll use unicode (UTF8) all throughout
+
+#include <boost/config/warning_disable.hpp>
+#include <boost/cstdint.hpp>
+#include <boost/spirit/include/qi.hpp>
+#include <boost/spirit/include/phoenix_core.hpp>
+#include <boost/spirit/include/phoenix_container.hpp>
+#include <boost/spirit/include/phoenix_statement.hpp>
+#include <boost/spirit/include/phoenix_operator.hpp>
+#include <boost/regex/pending/unicode_iterator.hpp>
+
+namespace scheme
+{
+ using boost::spirit::qi::grammar;
+ using boost::spirit::qi::rule;
+ using boost::spirit::unicode::char_;
+ using boost::spirit::unicode::space;
+ using boost::spirit::qi::eol;
+ using boost::spirit::qi::_val;
+ using boost::spirit::qi::_r1;
+ using boost::spirit::qi::_1;
+ using boost::spirit::qi::uint_parser;
+ using boost::phoenix::function;
+
+ typedef boost::spirit::char_encoding::unicode unicode;
+ typedef boost::uint32_t uchar; // a unicode code point
+
+ template <typename Iterator>
+ struct white_space : grammar<Iterator, unicode>
+ {
+ white_space() : white_space::base_type(start)
+ {
+ start =
+ space // tab/space/cr/lf
+ | ';' >> *(char_ - eol) >> eol // comments
+ ;
+ }
+
+ rule<Iterator, unicode> start;
+ };
+
+ namespace detail
+ {
+ struct push_utf8
+ {
+ template <typename S, typename C>
+ struct result { typedef void type; };
+
+ void operator()(std::string& utf8, uchar code_point) const
+ {
+ typedef std::back_insert_iterator<std::string> insert_iter;
+ insert_iter out_iter(utf8);
+ boost::utf8_output_iterator<insert_iter> utf8_iter(out_iter);
+ *utf8_iter++ = code_point;
+ }
+ };
+
+ struct push_esc
+ {
+ template <typename S, typename C>
+ struct result { typedef void type; };
+
+ void operator()(std::string& utf8, uchar c) const
+ {
+ switch (c)
+ {
+ case 'b': utf8 += '\b'; break;
+ case 't': utf8 += '\t'; break;
+ case 'n': utf8 += '\n'; break;
+ case 'f': utf8 += '\f'; break;
+ case 'r': utf8 += '\r'; break;
+ case '"': utf8 += '"'; break;
+ case '\\': utf8 += '\\'; break;
+ }
+ }
+ };
+ }
+
+ template <typename Iterator>
+ struct string : grammar<Iterator, unicode, std::string()>
+ {
+ string() : string::base_type(start)
+ {
+ uint_parser<uchar, 16> hex;
+ function<detail::push_utf8> push_utf8;
+ function<detail::push_esc> push_esc;
+
+ str_esc
+ = '\\'
+ >> ( ('u' >> hex) [push_utf8(_r1, _1)]
+ | char_("btnfr\\\"'") [push_esc(_r1, _1)]
+ )
+ ;
+
+ start
+ = '"'
+ >> *(str_esc(_val) | (char_ - '"') [push_utf8(_val, _1)])
+ >> '"'
+ ;
+ }
+
+ rule<Iterator, unicode, void(std::string&)> str_esc;
+ rule<Iterator, unicode, std::string()> start;
+ };
+}
+
+#endif


Boost-Commit list run by bdawes at acm.org, david.abrahams at rcn.com, gregod at cs.rpi.edu, cpdaniel at pacbell.net, john at johnmaddock.co.uk