Re: X3: How to write generic rules
Seth <[email protected]>
| Newsgroups | gmane.comp.parsers.spirit.general |
|---|---|
| Message-ID | <[email protected]> |
On 27-01-16 21:27, Mike Gresens wrote:
> Hi,
>
> lets say you have:
>
> user_rule = ...
> user_rule_def = ...
>
> group_rule = ...
> group_rule_def = ...
>
> BOOST_SPIRIT_DEFINE(user_rule, group_rule)
>
> Now you want to make a generic list_of_rule:
>
> list_of_rule = ??? MAGIC ???
>
> So you can use it later:
>
> users_rule_def = list_of_rule<user_rule>
> groups_rule_def = list_of_rule<groups_rule>
>
> How to do that?
>
How about:
auto list_of = [](auto p) { return x3::as_parser(p) % ","; };
auto user_rule = "user" >> x3::int_;
auto group_rule = "group" >> x3::bool_;
auto users_rule = list_of(user_rule);
auto groups_rule = list_of(group_rule);
I wouldn't overcomplicate things in X3.
You can always look at operator/list.hpp or directive/repeat.hpp to see
how these directives were made.
Here's a simple test: http://melpon.org/wandbox/permlink/m87LpfTAmATGxcyz
------------------------------------------------------------------------------
Site24x7 APM Insight: Get Deep Visibility into Application Performance
APM + Mobile APM + RUM: Monitor 3 App instances at just $35/Month
Monitor end-to-end web transactions and take corrective actions now
Troubleshoot faster and improve end-user experience. Signup Now!
http://pubads.g.doubleclick.net/gampad/clk?id=267308311&iu=/4140
_______________________________________________
Spirit-general mailing list
[email protected]
https://lists.sourceforge.net/lists/listinfo/spirit-general
test.cpp
(text/x-c++src, 1.1 KB)
#include <boost/spirit/home/x3.hpp>
#include <iostream>
namespace Parsing
{
namespace x3 = boost::spirit::x3;
auto list_of = [](auto p) { return x3::as_parser(p) % ","; };
auto user_rule = "user" >> x3::int_;
auto group_rule = "group" >> x3::bool_;
auto users_rule = list_of(user_rule);
auto groups_rule = list_of(group_rule);
}
template <typename T, typename P>
void test(std::string const& input, P const& parser) {
auto f = input.begin();
auto l = input.end();
std::vector<T> into;
bool ok = parse(f, l, parser, into);
if (ok) {
std::cout << "Parsed into: ";
std::copy(into.begin(), into.end(), std::ostream_iterator<T>(std::cout, " "));
std::cout << "\n";
} else {
std::cout << "Parsed failed";
}
if (f != l) {
std::cout << "Remaining input: '" << std::string(f,l) << "'\n-----\n";
}
}
int main()
{
std::cout << std::boolalpha;
test<int>("user1,user2,user42", Parsing::users_rule);
test<bool>("grouptrue,grouptrue,groupfalse", Parsing::groups_rule);
}