首页 > 解决方案 > Boost Spirit X3:错误:“...”中没有名为“size”的类型

问题描述

我试图解析成一个包含 std::string 和 std::vector 的结构,但是在使用 Boost Spirit 的 %-operator 时总是出错。

我已经尝试将列表解析隔离为单独的规则(source)和这个问题as<>的-directive

没有predicate_arguments规则,它可以完美运行。

错误很大,一些片段:

[...] error: static assertion failed: The parser expects tuple-like attribute type
[...] error: no type named 'size' in 'struct dec::predicate_query'
[...] error: no type named 'type' in 'struct boost::fusion::extension::size_impl<boost::fusion::non_fusion_tag>::apply<dec::predicate_query>'
[...] error: non-constant condition for static assertion

decfile_parser.cpp

namespace x3 = boost::spirit::x3;

x3::rule<class predicate_name, std::string> predicate_name = "predicate_name";
x3::rule<class predicate_query, dec::predicate_query> predicate_query = "predicate_query";
x3::rule<class predicate_arguments, std::vector<dec::predicate_argument_type>> predicate_arguments = "predicate_arguments";
x3::rule<class predicate_argument, dec::predicate_argument_type> predicate_argument = "predicate_argument";

auto const predicate_query_def = predicate_name >> '(' >> predicate_arguments  >> ')';
auto const predicate_arguments_def = predicate_argument % ',';
auto const predicate_name_def = *x3::char_("a-zA-Z");
// TODO: sortname
auto const predicate_argument_def = *x3::char_("a-zA-Z") | predicate_query;

decfile_parser::decfile_parser() {

}

void decfile_parser::parse_file(std::string filename) {
    int value = 0;
    std::string str("HoldsAt(Pos(), test)");
    std::string::iterator strbegin = str.begin();

    x3::phrase_parse(strbegin,
                     str.end(),
                     predicate_query,
                     x3::ascii::blank);

}

BOOST_SPIRIT_DEFINE(predicate_query, predicate_name, predicate_argument, predicate_arguments);

int main() {
    decfile_parser par;
    par.parse_file("test.e2");
}

decfile_parser.h

#include <boost/spirit/home/x3.hpp>
#include <boost/fusion/adapted/std_tuple.hpp>
#include <boost/fusion/include/adapt_struct.hpp>
#include <boost/spirit/include/phoenix.hpp>

#include <string>

#include "ast.h"

class decfile_parser {
public:
    decfile_parser();
    ~decfile_parser() = default;

    void parse_file(std::string filename);
};

ast.h

namespace dec {
    namespace x3 = boost::spirit::x3;


    struct predicate_query;
    typedef x3::variant<std::string, x3::forward_ast<predicate_query>> predicate_argument_type;

    struct predicate_query {
        std::string name;
        std::vector<predicate_argument_type> arguments;
    };
}

ast_adapted.h

#include <boost/fusion/include/adapt_struct.hpp>
#include "ast.h"

BOOST_FUSION_ADAPT_STRUCT(
        dec::predicate_query,
        (std::string, name),
        (std::vector<dec::predicate_argument_type>, arguments)
        )

编辑1:也许是因为他想解析namearguments放入一个容器中。

标签: c++booststruct

解决方案


我忘了导入ast_adapted.h到我的decfile_parser.h. 错误是因为结构当然不适合融合序列。


推荐阅读