c++ - boost::spirit 排列

标签 c++ boost boost-spirit boost-spirit-qi

我必须解析下面的一段文字

Camera {
    position 0 0 0
    direction 0 -1 0
    up 0 1 0
    FOVy 45
}

我选择了 boost:spirit,因为我不必处理 flex 或 bison。

我终于有了这个语法

struct camera_grammar :  qi::grammar<Iterator, camera(), ascii::space_type>
{
    qi::rule<Iterator, camera(), ascii::space_type> start;

    camera_grammar() : camera_grammar::base_type(start)
    {
        start %=
        lit("Camera")
        >> '{'
        >> (lit("position") >> float_ >> float_ >> float_) 
        >> (lit("direction") >> float_ >> float_ >> float_)
        >> (lit("up") >> float_ >> float_ >> float_)
        >> (lit("FOVy") >> int_)
        >> '}'
        ;
    }
};

问题是花括号内的部分甚至可以互换;我读过有关置换运算符 ^ 的内容,但我读到的是当至少一个操作数以任何顺序匹配时才匹配。我需要我的语法只在所有语法以任何顺序出现时才匹配,并且只匹配一次。

有人可以帮帮我吗?

最佳答案

Hartmut Kaiser 解释了如何做到这一点 in this article .

您需要按照文章中的描述定义no_empties_impl 类,然后声明一个函数

phoenix::function<no_empties_impl> const no_empties = no_empties_impl();

然后,在您的语法中,您需要为每个 positiondirectionup 定义规则视野。然后你的开始语法看起来像(未经测试):

start %=
lit("Camera")
>> '{'
>> position ^ direction ^ up ^ FOVy
>> '}'
    [qi::_pass = no_empties(qi::_0)]
;

关于c++ - boost::spirit 排列,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/10126680/

相关文章:

c++ - 为可变数量的内核编写多线程程序

linux - Linux 中的 Boost 1.48 编译 - 使用 Bjam 在输出文件中获取编译器名称?

c++ - 无法使用 Boost Spirit X3 解析空的 C++ 结构

C++ : convert date/time string to tm struct

c++ - 处理父类对象列表时调用子类的方法

c++ - 重新解释的指针未指向正确的内存位置

c++ - 使用 boost::bind 和重载函数的访问者模式

c++ - 如何使用 boost::json::value 调用无参数函数

c++ - 自定义预期失败的完整错误消息 (boost::spirit::x3)

c++ - Boost 是否因为不像 Boost 那样有罪?