将字符串填充到矢量中时,Boost Spirit X3没有匹配的调用引用

时间:2018-07-03 09:04:25

标签: c++ vector overloading boost-spirit

你好,我正在尝试使用Spirit x3将字符串填充到向量中,但是出现以下错误。代码直接来自文档,除了向量使用字符串。

error: no matching function for call to 
std::vector<std::__cxx11::basic_string<char> 
>::push_back(boost::spirit::x3::unused_type&)’
auto push_back = [&](auto& ctx){ slt.push_back(_attr(ctx)); };`

我的代码看起来像这样,我认为所有必需的包含物都在上面(它在类方法中):

#include <boost/spirit/home/x3.hpp>

#include <algorithm>
#include <bitset>
#include <fstream>
#include <iostream>
#include <iterator>
#include <map>
#include <sstream>
#include <stdexcept>
#include <string>
#include <vector>

namespace x3 = boost::spirit::x3;
namespace ascii = boost::spirit::x3::ascii;

using x3::double_;
using x3::phrase_parse;
using x3::_attr;
using x3::parse;
using x3::lit;
using x3::char_;
using x3::lexeme;
using x3::alpha;
using x3::alnum;
using x3::skip;
using ascii::space;

/*Something,something.......*/

auto name = x3::rule<class name>{}
                = char_("a-zA-Z") >> *char_("a-z_A-Z0-9");

auto args_l = x3::rule<class l>{}
                = " " >> (name % skip(space)[","]);

auto comment = x3::rule<class comment>{}
                = "//" >> *char_;

auto iter_start = line.begin();
auto iter_end = line.end();

vector<string> slt;

auto push_back = [&](auto& ctx){ slt.push_back(_attr(ctx)); };


bool result = parse(
        iter_start,
        iter_end,
        name[push_back] >> -args_l >> *(char_(" "))
);

/某事....... /

2 个答案:

答案 0 :(得分:1)

您的规则定义不公开属性。

就像@llonesmiz指出的那样,请解决此问题:

auto name = x3::rule<class name, std::string>{}
    = char_("a-zA-Z") >> *char_("a-z_A-Z0-9");

并查看 Live On Wandbox (boost-1.67)

  

注意:错误

     

如果您使用Boost 1.65-1.66,则会遇到   How to make a recursive rule in boost spirit x3 in VS2017,   (Live On Wandbox   在Boost 1.67(以及更早的版本,例如Live on Wandbox/Boost 1.64)中已修复的问题

#include <boost/spirit/home/x3.hpp>

namespace x3 = boost::spirit::x3;

namespace P {
    using namespace x3;

    auto name = x3::rule<class name, std::string>{}
        = char_("a-zA-Z") >> *char_("a-z_A-Z0-9");

    auto args_l = x3::rule<class l>{}
        = " " >> (name % skip(space)[","]);

    auto comment = x3::rule<class comment>{}
        = "//" >> *char_;
}

#include <iostream>
#include <iomanip>

int main() {
    std::string const line = "a90_b";
    auto iter_start = line.begin();
    auto iter_end = line.end();

    std::vector<std::string> slt;

    auto push_back = [&](auto& ctx){ slt.push_back(x3::_attr(ctx)); };

    bool result = parse(
            iter_start,
            iter_end,
            P::name[push_back] >> -P::args_l >> *x3::char_(" ")
        );

    for (auto& tok: slt) {
        std::cout << std::quoted(tok) << "\n";
    }

    if (iter_start!=iter_end)
        std::cout << "Remaining unparsed: " << std::quoted(std::string(iter_start, iter_end)) << "\n";

    return result? 0 : 255;
}

答案 1 :(得分:1)

在按anwering原样提出问题之后,我查看了您的代码。

奖金

考虑其余的代码,也许这就是您所追求的:

Live On Wandbox

#include <boost/spirit/home/x3.hpp>

namespace x3 = boost::spirit::x3;

namespace P {
    using namespace x3;

    auto name = x3::rule<class name, std::string>{}
        = lexeme [char_("a-zA-Z") >> *char_("a-z_A-Z0-9")];

    auto comment = x3::rule<class comment>{}
        = "//" >> *(char_-eol) 
        | "/*" >> *(char_ - "*/") >> "*/";

    auto args_l = skip(space|comment) [name % ','];
}

#include <iostream>
#include <iomanip>

int main() {
    for (std::string const line : { 
            "a90_b",
            "a90_b,   /*comment ignored*/ b8, //more stuff\nz",
        })
    {
        std::cout << "Parsing " << std::quoted(line) << "\n";

        auto iter_start = line.begin();
        auto iter_end   = line.end();

        std::vector<std::string> slt;
        bool result = parse(iter_start, iter_end, P::args_l, slt);

        if (result) {
                for (auto& tok: slt) {
                    std::cout << " -> " << std::quoted(tok) << "\n";
                }
        } else {
            std::cout << "Parsed failed\n";
        }

        if (iter_start!=iter_end) {
            std::cout << "Remaining unparsed: " << std::quoted(std::string(iter_start, iter_end)) << "\n";
        }
    }
}

打印

Parsing "a90_b"
 -> "a90_b"
Parsing "a90_b,   /*comment ignored*/ b8, //more stuff
z"
 -> "a90_b"
 -> "b8"
 -> "z"