$include_dir="/home/hyper-archives/boost-commit/include"; include("$include_dir/msg-header.inc") ?>
Subject: [Boost-commit] svn:boost r56564 - in trunk/boost/spirit/home/qi: detail operator
From: joel_at_[hidden]
Date: 2009-10-04 00:00:34
Author: djowel
Date: 2009-10-04 00:00:33 EDT (Sun, 04 Oct 2009)
New Revision: 56564
URL: http://svn.boost.org/trac/boost/changeset/56564
Log:
fixed alternative attribute handling
Text files modified: 
   trunk/boost/spirit/home/qi/detail/alternative_function.hpp |    20 +++++-----------                        
   trunk/boost/spirit/home/qi/operator/alternative.hpp        |    47 +++++++++++++++++++++++++++++++++++++-- 
   2 files changed, 50 insertions(+), 17 deletions(-)
Modified: trunk/boost/spirit/home/qi/detail/alternative_function.hpp
==============================================================================
--- trunk/boost/spirit/home/qi/detail/alternative_function.hpp	(original)
+++ trunk/boost/spirit/home/qi/detail/alternative_function.hpp	2009-10-04 00:00:33 EDT (Sun, 04 Oct 2009)
@@ -32,18 +32,17 @@
         }
 
         template <typename Component>
-        bool call(Component const& component, mpl::true_) const
+        bool operator()(Component const& component) const
         {
             // if Attribute is not a variant, then pass it as-is
             return component.parse(first, last, context, skipper, attr);
         }
-
-        template <typename Component>
-        bool call(Component const& component, mpl::false_) const
+        
+        template <typename Component, typename T>
+        bool operator()(Component const& component, mpl::identity<T>) const
         {
-            // if Attribute is a variant, then create an attribute for
-            // the Component with its expected type.
-            typename traits::attribute_of<Component, Context, Iterator>::type val;
+            // if Attribute is a variant, then create an attribute.
+            T val;
             if (component.parse(first, last, context, skipper, val))
             {
                 attr = val;
@@ -52,13 +51,6 @@
             return false;
         }
 
-        template <typename Component>
-        bool operator()(Component const& component) const
-        {
-            // return true if the parser succeeds
-            return call(component, spirit::traits::not_is_variant<Attribute>());
-        }
-
         Iterator& first;
         Iterator const& last;
         Context& context;
Modified: trunk/boost/spirit/home/qi/operator/alternative.hpp
==============================================================================
--- trunk/boost/spirit/home/qi/operator/alternative.hpp	(original)
+++ trunk/boost/spirit/home/qi/operator/alternative.hpp	2009-10-04 00:00:33 EDT (Sun, 04 Oct 2009)
@@ -19,7 +19,7 @@
 #include <boost/spirit/home/support/detail/what_function.hpp>
 #include <boost/spirit/home/support/unused.hpp>
 #include <boost/spirit/home/support/info.hpp>
-#include <boost/fusion/include/any.hpp>
+#include <boost/spirit/home/support/algorithm/any.hpp>
 #include <boost/fusion/include/mpl.hpp>
 #include <boost/fusion/include/for_each.hpp>
 
@@ -39,6 +39,23 @@
 
 namespace boost { namespace spirit { namespace qi
 {
+    namespace detail
+    {       
+        template <typename T>
+        struct get_variant_types;
+
+#define BOOST_SPIRIT_IDENTITY(z, n, data) mpl::identity<BOOST_PP_CAT(T, n)>
+        template <BOOST_VARIANT_ENUM_PARAMS(typename T)>
+        struct get_variant_types<variant<BOOST_VARIANT_ENUM_PARAMS(T)> >
+        {
+            typedef mpl::vector<
+                BOOST_PP_ENUM(
+                    BOOST_VARIANT_LIMIT_TYPES, BOOST_SPIRIT_IDENTITY, _)>
+            type;
+        };
+#undef BOOST_SPIRIT_IDENTITY
+    }
+    
     template <typename Elements>
     struct alternative : nary_parser<alternative<Elements> >
     {
@@ -65,9 +82,9 @@
 
         template <typename Iterator, typename Context
           , typename Skipper, typename Attribute>
-        bool parse(Iterator& first, Iterator const& last
+        bool parse_impl(Iterator& first, Iterator const& last
           , Context& context, Skipper const& skipper
-          , Attribute& attr) const
+          , Attribute& attr, mpl::true_) const
         {
             detail::alternative_function<Iterator, Context, Skipper, Attribute>
                 f(first, last, context, skipper, attr);
@@ -75,6 +92,30 @@
             // return true if *any* of the parsers succeed
             return fusion::any(elements, f);
         }
+        
+        template <typename Iterator, typename Context
+          , typename Skipper, typename Attribute>
+        bool parse_impl(Iterator& first, Iterator const& last
+          , Context& context, Skipper const& skipper
+          , Attribute& attr, mpl::false_) const
+        {
+            detail::alternative_function<Iterator, Context, Skipper, Attribute>
+                f(first, last, context, skipper, attr);
+
+            // return true if *any* of the parsers succeed
+            typename detail::get_variant_types<Attribute>::type vtypes;
+            return spirit::any(elements, vtypes, f);
+        }
+        
+        template <typename Iterator, typename Context
+          , typename Skipper, typename Attribute>
+        bool parse(Iterator& first, Iterator const& last
+          , Context& context, Skipper const& skipper
+          , Attribute& attr) const
+        {
+            return parse_impl(first, last, context, skipper, attr,
+                spirit::traits::not_is_variant<Attribute>());
+        }
 
         template <typename Context>
         info what(Context& context) const