|
Boost-Commit : |
Subject: [Boost-commit] svn:boost r58824 - in trunk: boost/spirit/home/qi/detail boost/spirit/home/support libs/spirit/test/qi
From: hartmut.kaiser_at_[hidden]
Date: 2010-01-08 22:51:22
Author: hkaiser
Date: 2010-01-08 22:51:21 EST (Fri, 08 Jan 2010)
New Revision: 58824
URL: http://svn.boost.org/trac/boost/changeset/58824
Log:
Spirit: fixing attribute handling in sequences
Text files modified:
trunk/boost/spirit/home/qi/detail/assign_to.hpp | 28 ++++++++++++++++++++++++++--
trunk/boost/spirit/home/support/attributes_fwd.hpp | 3 +++
trunk/boost/spirit/home/support/container.hpp | 22 ++++++++++++++++++++++
trunk/libs/spirit/test/qi/lit.cpp | 2 ++
trunk/libs/spirit/test/qi/sequence.cpp | 13 ++++++++++---
5 files changed, 63 insertions(+), 5 deletions(-)
Modified: trunk/boost/spirit/home/qi/detail/assign_to.hpp
==============================================================================
--- trunk/boost/spirit/home/qi/detail/assign_to.hpp (original)
+++ trunk/boost/spirit/home/qi/detail/assign_to.hpp 2010-01-08 22:51:21 EST (Fri, 08 Jan 2010)
@@ -16,8 +16,10 @@
#include <boost/spirit/home/qi/detail/construct.hpp>
#include <boost/spirit/home/support/unused.hpp>
#include <boost/spirit/home/support/attributes_fwd.hpp>
+#include <boost/spirit/home/support/container.hpp>
#include <boost/spirit/home/phoenix/core/actor.hpp>
#include <boost/ref.hpp>
+#include <boost/range/iterator_range.hpp>
namespace boost { namespace spirit { namespace traits
{
@@ -32,7 +34,12 @@
static void
call(Iterator const& first, Iterator const& last, Attribute& attr)
{
- attr = Attribute(first, last);
+ if (is_empty(attr))
+ attr = Attribute(first, last);
+ else {
+ for (Iterator i = first; i != last; ++i)
+ push_back(attr, *i);
+ }
}
};
@@ -44,7 +51,24 @@
call(Iterator const& first, Iterator const& last
, reference_wrapper<Attribute> attr)
{
- attr = Attribute(first, last);
+ if (is_empty(attr))
+ attr = Attribute(first, last);
+ else {
+ for (Iterator i = first; i != last; ++i)
+ push_back(attr, *i);
+ }
+ }
+ };
+
+ template <typename Iterator>
+ struct assign_to_attribute_from_iterators<
+ iterator_range<Iterator>, Iterator>
+ {
+ static void
+ call(Iterator const& first, Iterator const& last
+ , iterator_range<Iterator>& attr)
+ {
+ attr = iterator_range<Iterator>(first, last);
}
};
Modified: trunk/boost/spirit/home/support/attributes_fwd.hpp
==============================================================================
--- trunk/boost/spirit/home/support/attributes_fwd.hpp (original)
+++ trunk/boost/spirit/home/support/attributes_fwd.hpp 2010-01-08 22:51:21 EST (Fri, 08 Jan 2010)
@@ -70,6 +70,9 @@
template <typename Container, typename T, typename Enable = void>
struct push_back_container;
+ template <typename Container, typename Enable = void>
+ struct is_empty_container;
+
///////////////////////////////////////////////////////////////////////
// Determine the iterator type of the given container type
///////////////////////////////////////////////////////////////////////
Modified: trunk/boost/spirit/home/support/container.hpp
==============================================================================
--- trunk/boost/spirit/home/support/container.hpp (original)
+++ trunk/boost/spirit/home/support/container.hpp 2010-01-08 22:51:21 EST (Fri, 08 Jan 2010)
@@ -327,6 +327,28 @@
///////////////////////////////////////////////////////////////////////////
template <typename Container, typename Enable/* = void*/>
+ struct is_empty_container
+ {
+ static bool call(Container const& c)
+ {
+ return c.empty();
+ }
+ };
+
+ template <typename Container>
+ bool is_empty(Container const& c)
+ {
+ return is_empty_container<Container>::call(c);
+ }
+
+ template <typename T>
+ bool is_empty(unused_type)
+ {
+ return true;
+ }
+
+ ///////////////////////////////////////////////////////////////////////////
+ template <typename Container, typename Enable/* = void*/>
struct begin_container
{
static typename container_iterator<Container>::type call(Container& c)
Modified: trunk/libs/spirit/test/qi/lit.cpp
==============================================================================
--- trunk/libs/spirit/test/qi/lit.cpp (original)
+++ trunk/libs/spirit/test/qi/lit.cpp 2010-01-08 22:51:21 EST (Fri, 08 Jan 2010)
@@ -84,8 +84,10 @@
std::string s;
BOOST_TEST((test_attr("kimpo", string("kimpo"), s)));
BOOST_TEST(s == "kimpo");
+ s.clear();
BOOST_TEST((test_attr(L"kimpo", string(L"kimpo"), s)));
BOOST_TEST(s == "kimpo");
+ s.clear();
BOOST_TEST((test_attr("x", string("x"), s)));
BOOST_TEST(s == "x");
}
Modified: trunk/libs/spirit/test/qi/sequence.cpp
==============================================================================
--- trunk/libs/spirit/test/qi/sequence.cpp (original)
+++ trunk/libs/spirit/test/qi/sequence.cpp 2010-01-08 22:51:21 EST (Fri, 08 Jan 2010)
@@ -145,14 +145,21 @@
BOOST_TEST(v[0] == 'a');
BOOST_TEST(v[1] == 'b');
BOOST_TEST(v[2] == 'c');
+ }
+
+ { // alternative forms of attributes. Allow sequences to take in
+ // stl containers.
+ std::string s;
+ BOOST_TEST(test_attr("foobar", string("foo") >> string("bar"), s));
+ BOOST_TEST(s == "foobar");
}
- // alternative forms of attributes. Allow sequences to take in
- // stl containers of stl containers.
+// // alternative forms of attributes. Allow sequences to take in
+// // stl containers of stl containers.
// {
// // this use case still does not compile, needs some additional work
-//
+//
// std::vector<std::string> v;
// BOOST_TEST(test_attr("abc1,abc2,abc3",
// *~char_(',') >> *(',' >> *~char_(',')), v));
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