假设我有一个我想用灵气解析成的结构,它是这样定义的:
struct data_
{
bool export;
std::wstring name;
data_() : export(false) {}
};
此外,假设结构已适应这样的融合:
BOOST_FUSION_ADAPT_STRUCT(
data_,
(bool, export)
(std::wstring, name)
)
关联的规则是:
qi::rule<Iterator, data_(), skipper<Iterator> > rule_data;
rule_data = -lexeme["SpecialText" >> !(alnum | '_')] [ boost::phoenix::at_c<0> = true ] // If this string is found, , set "export" to true
> lexeme["Name" >> !(alnum | '_')] // this is supposed to go into the "name" member
到目前为止,这个编译非常好。但是,“name”现在仍然是空的!
所以本质上,我要问的是:鉴于“SpecialText”在“Name”之前,我将如何正确合成一个用于“export”的 bool 属性,而不是一个字符串?
编辑 在为此烦恼之后,我偶然发现了“matches[]”解析器,它似乎可以满足我的要求。
尽管如此,问题仍然存在于一般形式,例如,如果我想返回某个字符串或其他数据类型而不是bool。 本质上,如何通过语义操作设置结构属性的特定成员。
最佳答案
如何设置结构成员。
选项 1(phx::bind
)
给定一个结构S
struct S
{
int field1;
std::string field2;
int target_field;
bool field3;
};
您可以像这样分配给一个字段(例如 target_field
):
rule<It, S()> p = int_ [ phx::bind(&S::target_field, _val) = _1 ];
现在,您可以通过执行以下操作使 bind
更具可读性:
auto target_field_ = phx::bind(&S::target_field, _val);
p = int_ [ target_field_ = _1 ];
概念验证: live on Coliru
#include "boost/spirit/include/qi.hpp"
#include "boost/spirit/include/phoenix.hpp"
namespace qi = boost::spirit::qi;
namespace phx = boost::phoenix;
typedef std::string::const_iterator It;
struct S
{
int field1;
std::string field2;
int target_field;
bool field3;
};
int main()
{
const std::string input("42");
It f(begin(input)), l(end(input));
S instance;
using namespace qi;
rule<It, S()> p = int_ [ phx::bind(&S::target_field, _val) = _1 ];
// or, alternatively:
auto target_field_ = phx::bind(&S::target_field, _val);
p = int_ [ target_field_ = _1 ];
if (parse(f, l, p, instance))
std::cout << "Parsed: " << instance.target_field;
}
选项 2(融合序列)
您可以使用适应将结构视为融合序列:
#include "boost/fusion/adapted/struct.hpp"
BOOST_FUSION_ADAPT_STRUCT(S, (int, field1)(std::string, field2)(int, target_field)(bool, field3))
现在您可以在语义操作中对这些序列使用 phoenix lazy 函数:
rule<It, S()> p = int_ [ phx::at_c<2>(_val) = _1 ];
我不喜欢这种风格(因为它会将一个富有表现力的结构“降级”为......各种元组),但它可能会派上用场。 <强> Live on Coliru
关于c++ - Boost Spirit Qi Custom Syntesized Attribute(通过语义操作设置结构属性的特定成员),我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/18602818/