gpt4 book ai didi

c++ - 语义操作(使用 _val 和 _attr)如何影响 %= 和 x3::rule 的 force_attribute=true 的规则定义?

转载 作者:行者123 更新时间:2023-11-30 04:53:09 27 4
gpt4 key购买 nike

给定语义 Actor

template<typename ValueType>
class divide
{
public:
divide(ValueType value) : divisor{value} {}

template<typename ContextType>
void operator()(ContextType& context) const
{
_val(context) /= divisor;
}
private:
const ValueType divisor;
};

看来我是在强调语义行为的存在会抑制属性合成(或传播?),即

const auto norm = x3::rule<struct _, double>{"norm"}
= x3::double_[normalize{100.}];

给我值 0。

所以我尝试使用 %=

强制属性传播
const auto norm_rule = x3::rule<struct _, double>{"norm"}
%= x3::double_[normalize{100.}];

这给了我预期的解析值除以 100。

然后我发现 x3::rule 有第三个模板参数,bool force_attribute,并注意到

const auto norm_rule = x3::rule<struct _, double, true>{"norm"}
= x3::double_[divide{100.}];

将值除以 100 得到想要的结果。

进一步试验,我还发现我可以改为定义 divide::operator() 如下:

void operator()(ContextType& context)
{
_attr(context) = _val(context) / divisor;
}

最后一个似乎将语义参与者强烈耦合/谴责到规则的顶层,因为它作用于第一个规则的属性 _attr 而不是值 _val 它所附加的解析器。

我的推论是否正确

  1. %= 与设置第三个x3::rule 模板参数force_attribute 为true 是一样的吗?
  2. 这种类型的值处理语义操作应该只在 _val 上工作,以便它们在附加的解析器上工作,而不是在层次结构中遇到的第一个 rule 上工作?

我知道这些看似无关的问题,但它们确实相互关联,因为我正在尝试处理已解析的数字( float )并以多种方式将其转换为 uint8。完全完整:我有工作代码(数字内容 here 和我正在构建/解析的实际内容 here ),但它似乎不必要地复杂(由于上述原因,我似乎需要每个类型/值的规则转换,这看起来很愚蠢。

最佳答案

it seems I'm hitting the fact that the presence of semantic actions inhibit attribute synthesis (or propagation?)

原来如此,这个行为是从 Qi ( qi::rule docs , How Do Rules Propagate Their Attributes? ) 复制过来的。

相关代码部分:call site , handling .

%= is the same as setting the third x3::rule template parameter force_attribute to true?

是的,没有文档,看代码boost/spirit/home/x3/nonterminal/rule.hpp .

Experimenting further, I also discovered I could instead define divide::operator() as follows:

void operator()(ContextType& context)
{
_attr(context) = _val(context) / divisor;
}

This last one seems to strongly couple/condemn the semantic actor to a rule's top level, as it acts on the attribute _attr of the first rule instead of the value _val of a parser to which it is attached.

你几乎答对了,但交换了它们。应该是_val(context) = _attr(context)/divisor,详情如下。

This type of value-processing semantic actions should exclusively work on _val so they work on the attached parser instead of the first rule encountered in the hierarchy?

semantic actions documentation描述什么是 _val_attr:

Function  Description                                         Example
-------- -------------------------------------------------- -----------------------
_val A reference to the attribute of the innermost rule _val(ctx) = "Gotya!"
that directly or indirectly invokes the parser p
_attr A reference to the attribute of the parser p _val(ctx) += _attr(ctx)

它们在特定情况下的表现取决于make_attribute/transform_attribute 特征。默认情况下,它们将引用相同的值,直到您拥有具有不同属性类型 ( relevant code) 的嵌套规则。

附言至于为什么会这样,我无话可说。我看到许多 Spirit 用户到处都使用 %=,因为直觉上它应该是默认设置,您可以使用 omit 指令手动禁用传播。此外,当您在 repeat 指令 ( ticket 13313 ) 上使用惰性值时,Qi 会因为这种机制而存在一些错误。

关于c++ - 语义操作(使用 _val 和 _attr)如何影响 %= 和 x3::rule 的 force_attribute=true 的规则定义?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/53969454/

27 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com