Spirit:无法在其规则定义中使用 x3::skip(skipper)[some recursive rule]
Posted
技术标签:
【中文标题】Spirit:无法在其规则定义中使用 x3::skip(skipper)[some recursive rule]【英文标题】:Spirit: Not able to use x3::skip(skipper)[some recursive rule] in its rule definition 【发布时间】:2017-07-24 13:44:56 【问题描述】:假设我们要解析这样的递归块。当“skip_comments_tag
”作为前缀添加到块中时,我们会递归地跳过该块中的所有 cmets(/*...*/
)。
skip_comments_tag
/*comments*/
/*comments*/
很容易想出像Coliru 这样的递归解析器。
namespace Parser
auto const ruleComment = x3::lit("/*") >> *(x3::char_ - "*/") >> "*/" | x3::space;
x3::rule<struct SBlockId> const ruleBlock;
auto const ruleBlock_def = x3::lit('') >> *(ruleBlock | "skip_comments_tag" >> x3::skip(ruleComment)[ruleBlock]) >> '';
BOOST_SPIRIT_DEFINE(ruleBlock)
但它不会编译(当调用parse
函数时),因为它会生成一个无限上下文(由x3::make_context
在x3::skip_directive
中)。 x3::no_case
和 x3::with
也有这个问题,因为它们在实现中都使用了x3::make_context
。
问题:
-
是否总有更好的方法来为这种类型编写解析器?
避免此类编译错误的问题以及如何避免?
或者
x3::make_context
的实现是否被认为在此类问题上存在缺陷?
【问题讨论】:
【参考方案1】:老实说,我确实认为这是make_context
设施中的一个限制,是的,它曾经困扰过我。
您可以通过使用 TU 分隔(BOOST_SPIRIT_DECLARE
、BOOST_SPIRIT_DEFINE
和
BOOST_SPIRIT_INSTANTIATE
宏)。
老实说,我会在邮件列表中报告它:[spirit-general]
另见http://boost.2283326.n4.nabble.com/Horrible-compiletimes-and-memory-usage-while-compiling-a-parser-with-X3-td4689104i20.html(FWIW 我觉得“序列分区”问题无关)
【讨论】:
以上是关于Spirit:无法在其规则定义中使用 x3::skip(skipper)[some recursive rule]的主要内容,如果未能解决你的问题,请参考以下文章