You are probably looking for container attribute settings points:
For your type, it will look like this:
namespace boost { namespace spirit { namespace traits { template <typename T> struct container_value<SimpleLinkList<T>, void> { typedef T type; }; template <typename T> struct push_back_container<SimpleLinkList<T>, T, void> { static bool call(SimpleLinkList<T>& c, T const& val) { c.push_back(val); return true; } }; }}}
Simple demo (using the dummy implementation of SimpleLinkList ):
struct AbstractDataType { int number; SimpleLinkList<int> list1, list2; }; BOOST_FUSION_ADAPT_STRUCT(AbstractDataType, (int, number)(SimpleLinkList<int>, list1)(SimpleLinkList<int>, list2)) template<typename Iterator> struct parser_expression : qi::grammar<Iterator, AbstractDataType(), qi::space_type> { parser_expression() : parser_expression::base_type(start) { list = '[' >> -(qi::int_ % ',') >> ']'; start = qi::int_ >> list >> -list >> '='; BOOST_SPIRIT_DEBUG_NODES((list)(start)) } qi::rule<Iterator, AbstractDataType(), qi::space_type> start; qi::rule<Iterator, SimpleLinkList<int>(), qi::space_type> list; };
Note
- I replaced
qi::char_ with (implicit) qi::lit where possible, because you actually don't want to parse punctuation characters in an attribute (right?) - I used the list parser operator
% instead of an extended alternative - I used the parser operator
- to make the list of elements optional (allow null elements) - Similarly,
list >> -list is used to make the second list optional together.
The following test files:
void test(const std::string input) { static const parser_expression<std::string::const_iterator> p; AbstractDataType parsed; auto f(input.begin()), l(input.end()); bool ok = qi::phrase_parse(f, l, p, qi::space, parsed); if (ok) std::cout << "Result: " << parsed.number << " " << parsed.list1 << parsed.list2 << "\n"; else std::cout << "Parse failed\n"; if (f!=l) std::cout << "Unparsed: '" << std::string(f,l) << "'\n"; } int main() { test("1 [2, 3, 4] [5, 6] ="); test("2 [] [6, 7] ="); test("3 [4, 5, 6] [ ] ="); test("4 [5, 6, 7] ="); }
Print the output:
Result: 1 [2 3 4 ][5 6 ] Result: 2 [][6 7 ] Result: 3 [4 5 6 ][] Result: 4 [5 6 7 ][]
See all integrated: http://ideone.com/odqhBz . Link Prevention:
// #define BOOST_SPIRIT_DEBUG #include <boost/fusion/adapted.hpp> #include <boost/spirit/include/qi.hpp>