$include_dir="/home/hyper-archives/boost-commit/include"; include("$include_dir/msg-header.inc") ?>
Subject: [Boost-commit] svn:boost r56387 - in trunk/libs/spirit: example/karma example/qi repository/test/karma
From: hartmut.kaiser_at_[hidden]
Date: 2009-09-26 12:24:21
Author: hkaiser
Date: 2009-09-26 12:24:20 EDT (Sat, 26 Sep 2009)
New Revision: 56387
URL: http://svn.boost.org/trac/boost/changeset/56387
Log:
Spirit: started to add attribute transformation capabilities, new examples
Added:
   trunk/libs/spirit/example/karma/reorder_struct.cpp   (contents, props changed)
   trunk/libs/spirit/example/qi/reorder_struct.cpp   (contents, props changed)
Text files modified: 
   trunk/libs/spirit/example/karma/CMakeLists.txt      |     9 +++++----                               
   trunk/libs/spirit/example/karma/Jamfile             |     9 +++++----                               
   trunk/libs/spirit/example/qi/CMakeLists.txt         |     1 +                                       
   trunk/libs/spirit/example/qi/Jamfile                |     1 +                                       
   trunk/libs/spirit/repository/test/karma/subrule.cpp |     2 +-                                      
   5 files changed, 13 insertions(+), 9 deletions(-)
Modified: trunk/libs/spirit/example/karma/CMakeLists.txt
==============================================================================
--- trunk/libs/spirit/example/karma/CMakeLists.txt	(original)
+++ trunk/libs/spirit/example/karma/CMakeLists.txt	2009-09-26 12:24:20 EDT (Sat, 26 Sep 2009)
@@ -8,9 +8,9 @@
 
 boost_add_executable(actions)
 boost_add_executable(basic_facilities DEPENDS boost_date_time)
-boost_add_executable(calc2_ast_dump)
-boost_add_executable(calc2_ast_rpn)
-boost_add_executable(calc2_ast_vm)
+boost_add_executable(karma_calc2_ast_dump calc2_ast_dump.cpp)
+boost_add_executable(karma_calc2_ast_rpn calc2_ast_rpn.cpp)
+boost_add_executable(karma_calc2_ast_vm calc2_ast_vm.cpp)
 boost_add_executable(classify_char)
 boost_add_executable(karma_complex_number complex_number.cpp)
 boost_add_executable(karma_complex_number_easier complex_number_easier.cpp)
@@ -22,7 +22,8 @@
 boost_add_executable(mini_xml_karma)
 boost_add_executable(printf_style_double_format)
 boost_add_executable(quick_start1)
-boost_add_executable(reference)
+boost_add_executable(karma_reference reference.cpp)
+boost_add_executable(karma_reorder_struct reorder_struct.cpp)
 
 
 
Modified: trunk/libs/spirit/example/karma/Jamfile
==============================================================================
--- trunk/libs/spirit/example/karma/Jamfile	(original)
+++ trunk/libs/spirit/example/karma/Jamfile	2009-09-26 12:24:20 EDT (Sat, 26 Sep 2009)
@@ -11,9 +11,9 @@
 
 exe actions_example : actions.cpp ;
 exe basic_facilities : basic_facilities.cpp /boost//date_time ;
-exe calc2_ast_dump : calc2_ast_dump.cpp ;
-exe calc2_ast_rpn : calc2_ast_rpn.cpp ;
-exe calc2_ast_vm : calc2_ast_vm.cpp ;
+exe karma_calc2_ast_dump : calc2_ast_dump.cpp ;
+exe karma_calc2_ast_rpn : calc2_ast_rpn.cpp ;
+exe karma_calc2_ast_vm : calc2_ast_vm.cpp ;
 exe classify_char : classify_char.cpp ;
 exe karma_complex_number : complex_number.cpp ;
 exe karma_complex_number_easier : complex_number_easier.cpp ;
@@ -25,5 +25,6 @@
 exe mini_xml_karma : mini_xml_karma.cpp ;
 exe printf_style_double_format : printf_style_double_format.cpp ;
 exe quick_start1 : quick_start1.cpp ;
-exe reference : reference.cpp ;
+exe karma_reference : reference.cpp ;
+exe karma_reorder_struct : reorder_struct.cpp ;
 
Added: trunk/libs/spirit/example/karma/reorder_struct.cpp
==============================================================================
--- (empty file)
+++ trunk/libs/spirit/example/karma/reorder_struct.cpp	2009-09-26 12:24:20 EDT (Sat, 26 Sep 2009)
@@ -0,0 +1,105 @@
+//  Copyright (c) 2001-2009 Hartmut Kaiser
+// 
+//  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)
+
+//  The main purpose of this example is to show how a single fusion sequence
+//  can be used to generate output of the elements in different sequences
+
+#include <boost/config/warning_disable.hpp>
+#include <boost/spirit/include/karma.hpp>
+#include <boost/fusion/include/struct.hpp>
+#include <boost/fusion/include/nview.hpp>
+#include <boost/assign/std/vector.hpp>
+
+namespace fusion = boost::fusion;
+namespace karma = boost::spirit::karma;
+
+///////////////////////////////////////////////////////////////////////////////
+namespace client
+{
+    //  Our employee struct
+    struct employee
+    {
+        std::string surname;
+        std::string forename;
+        int age;
+        double salary;
+        std::string department;
+    };
+
+    // define iterator type
+    typedef std::back_insert_iterator<std::string> iterator_type;
+
+    // This is the output routine taking a format description and the data to
+    // print
+    template <typename Generator, typename Sequence>
+    void generate(Generator const& g, Sequence const& s)
+    {
+        std::string generated;
+        iterator_type sink(generated);
+        karma::generate(sink, g, s);
+        std::cout << generated << std::endl;
+    }
+}
+
+// We need to tell fusion about our employee struct to make it a first-class 
+// fusion citizen. This has to be in global scope. Note that we don't need to 
+// list the members of our struct in the same sequence a they are defined
+BOOST_FUSION_ADAPT_STRUCT(
+    client::employee,
+    (int, age)
+    (std::string, surname)
+    (std::string, forename)
+    (std::string, department)
+    (double, salary)
+)
+
+///////////////////////////////////////////////////////////////////////////////
+int main()
+{
+    std::string str;
+
+    // some employees
+    client::employee john = { "John", "Smith", 25, 2000.50, "Sales" };
+    client::employee mary = { "Mary", "Higgins", 23, 2200.36, "Marketing" };
+    client::employee tom = { "Tom", "Taylor", 48, 3200.00, "Boss" };
+
+    // print data about employees in different formats
+    {
+        // print forename and age
+        client::generate(
+            karma::string << ", " << karma::int_, 
+            fusion::as_nview<2, 0>(john));
+
+        // print surname, forename, and salary
+        client::generate(
+            karma::string << ' ' << karma::string << ": " << karma::double_, 
+            fusion::as_nview<1, 2, 4>(mary));
+
+        // print forename, age, and department
+        client::generate(
+            karma::string << ": " << karma::int_ << " (" << karma::string << ')', 
+            fusion::as_nview<2, 0, 3>(tom));
+    }
+
+    // now make a list of all employees and print them all
+    std::vector<client::employee> employees;
+    {
+        using namespace boost::assign;
+        employees += john, mary, tom;
+    }
+
+    // print surname, forename, and salary for all employees
+    {
+        typedef 
+            fusion::result_of::as_nview<client::employee const, 1, 2, 4>::type 
+        names_and_salary;
+
+        karma::rule<client::iterator_type, names_and_salary()> r =
+            karma::string << ' ' << karma::string << ": " << karma::double_;
+
+        client::generate(r % karma::eol, employees);
+    }
+    return 0;
+}
Modified: trunk/libs/spirit/example/qi/CMakeLists.txt
==============================================================================
--- trunk/libs/spirit/example/qi/CMakeLists.txt	(original)
+++ trunk/libs/spirit/example/qi/CMakeLists.txt	2009-09-26 12:24:20 EDT (Sat, 26 Sep 2009)
@@ -22,6 +22,7 @@
 boost_add_executable( num_list2  num_list2.cpp )
 boost_add_executable( num_list3  num_list3.cpp )
 boost_add_executable( num_list4  num_list4.cpp )
+boost_add_executable( reorder_struct  reorder_struct.cpp )
 
 boost_add_executable( calc1  calc1.cpp )
 boost_add_executable( calc2  calc2.cpp )
Modified: trunk/libs/spirit/example/qi/Jamfile
==============================================================================
--- trunk/libs/spirit/example/qi/Jamfile	(original)
+++ trunk/libs/spirit/example/qi/Jamfile	2009-09-26 12:24:20 EDT (Sat, 26 Sep 2009)
@@ -23,6 +23,7 @@
 exe num_list2 : num_list2.cpp ;
 exe num_list3 : num_list3.cpp ;
 exe num_list4 : num_list4.cpp ;
+exe reorder_struct : reorder_struct.cpp ;
 
 exe calculator1 : calc1.cpp ;
 exe calculator2 : calc2.cpp ;
Added: trunk/libs/spirit/example/qi/reorder_struct.cpp
==============================================================================
--- (empty file)
+++ trunk/libs/spirit/example/qi/reorder_struct.cpp	2009-09-26 12:24:20 EDT (Sat, 26 Sep 2009)
@@ -0,0 +1,130 @@
+//  Copyright (c) 2001-2009 Hartmut Kaiser
+// 
+//  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)
+
+//  The main purpose of this example is to show how a single fusion sequence
+//  can be filled from a parsed input of the elements in different sequences
+
+#include <boost/config/warning_disable.hpp>
+#include <boost/mpl/print.hpp>
+#include <boost/spirit/include/qi.hpp>
+#include <boost/fusion/include/struct.hpp>
+#include <boost/fusion/include/nview.hpp>
+#include <boost/foreach.hpp>
+
+namespace fusion = boost::fusion;
+namespace qi = boost::spirit::qi;
+
+///////////////////////////////////////////////////////////////////////////////
+namespace client
+{
+    //  Our employee struct
+    struct employee
+    {
+        std::string surname;
+        std::string forename;
+        int age;
+        double salary;
+        std::string department;
+    };
+
+    // define iterator type
+    typedef std::string::const_iterator iterator_type;
+
+    // This is the output routine taking a format description and the data to
+    // print
+    template <typename Parser, typename Sequence>
+    bool parse(std::string const& input, Parser const& p, Sequence& s)
+    {
+        iterator_type begin = input.begin();
+        return qi::parse(begin, input.end(), p, s);
+    }
+}
+
+// We need to tell fusion about our employee struct to make it a first-class 
+// fusion citizen. This has to be in global scope. Note that we don't need to 
+// list the members of our struct in the same sequence a they are defined
+BOOST_FUSION_ADAPT_STRUCT(
+    client::employee,
+    (int, age)
+    (std::string, surname)
+    (std::string, forename)
+    (std::string, department)
+    (double, salary)
+)
+
+///////////////////////////////////////////////////////////////////////////////
+// that's the different types we need to reorder the attributes
+typedef fusion::result_of::as_nview<client::employee, 2, 0>::type name_and_age;
+typedef fusion::result_of::as_nview<client::employee, 1, 2, 4>::type names_and_salary;
+typedef fusion::result_of::as_nview<client::employee, 2, 0, 3>::type name_age_and_department;
+
+///////////////////////////////////////////////////////////////////////////////
+int main()
+{
+    std::string str;
+
+    // some employees
+    client::employee john;
+    client::employee mary;
+    client::employee tom;
+
+    // print data about employees in different formats
+    {
+        // parse forename and age only
+        name_and_age johnview(fusion::as_nview<2, 0>(john));
+        bool r = client::parse(
+            "John, 25",
+            *(qi::char_ - ',') >> ", " >> qi::int_, 
+            johnview);
+        if (r) {
+            std::cout << "Parsed: " << john.forename << ", " << john.age 
+                      << std::endl;
+        }
+
+        // parse surname, forename, and salary
+        names_and_salary maryview(fusion::as_nview<1, 2, 4>(mary));
+        r = client::parse(
+            "Higgins, Mary: 2200.36",
+            *(qi::char_ - ',') >> ", " >> *(qi::char_ - ':') >> ": " >> qi::double_, 
+            maryview);
+        if (r) {
+            std::cout << "Parsed: " << mary.forename << ", " << mary.surname 
+                      << ", " << mary.salary << std::endl;
+        }
+
+        // parse forename, age, and department
+        name_age_and_department tomview(fusion::as_nview<2, 0, 3>(tom));
+        client::parse(
+            "Tom: 48 (Boss)",
+            *(qi::char_ - ':') >> ": " >> qi::int_ >> " (" >> *(qi::char_ - ')') >> ')', 
+            tomview);
+        if (r) {
+            std::cout << "Parsed: " << tom.forename << ", " << tom.age
+                      << ", " << tom.department << std::endl;
+        }
+    }
+
+    // now parse a list of several employees and print them all
+    std::vector<client::employee> employees;
+
+    // parse surname, forename, and salary for all employees
+    {
+        qi::rule<client::iterator_type, names_and_salary()> r =
+            *(qi::char_ - ',') >> ", " >> *(qi::char_ - ',') >> ", " >> qi::double_;
+
+        bool result = client::parse(
+            "John, Smith, 2000.50\n" "Mary, Higgins, 2200.36\n" "Tom, Taylor, 3200.00\n",
+            r % qi::eol, employees);
+
+        std::cout << "Parsed: " << std::endl;
+        BOOST_FOREACH(client::employee const& e, employees) 
+        {
+            std::cout << e.forename << ", " << e.surname << ", " << e.salary 
+                      << std::endl;
+        }
+    }
+    return 0;
+}
+
Modified: trunk/libs/spirit/repository/test/karma/subrule.cpp
==============================================================================
--- trunk/libs/spirit/repository/test/karma/subrule.cpp	(original)
+++ trunk/libs/spirit/repository/test/karma/subrule.cpp	2009-09-26 12:24:20 EDT (Sat, 26 Sep 2009)
@@ -31,7 +31,7 @@
     using namespace boost;
     using namespace boost::spirit;
     using namespace boost::spirit::karma;
-    using namespace boost::spirit::ascii;
+//    using namespace boost::spirit::ascii;
     using boost::spirit::repository::karma::subrule;
 
     typedef spirit_test::output_iterator<char>::type outiter_type;