Boost Spirit调试枚举类(c+;+;11)编译错误

Boost Spirit调试枚举类(c+;+;11)编译错误,boost,c++11,enums,boost-spirit,boost-spirit-qi,Boost,C++11,Enums,Boost Spirit,Boost Spirit Qi,我正在尝试调试一个简单的结构,它包含一个带有BOOST\u SPIRIT\u debug\u节点的枚举类,但是我总是得到编译错误“C:\BOOST\BOOST\SPIRIT\home\support\attributes。hpp:1226:错误:无法将'std::basic\u ostream'左值绑定到'std::basic\u ostream&&near'out 我不知道为什么会出现这样的右值错误,我试图为操作添加一个手动重载“因为编译器通常会列出所有可用的运算符库的候选重载。我试图定义op

我正在尝试调试一个简单的结构,它包含一个带有BOOST\u SPIRIT\u debug\u节点的枚举类,但是我总是得到编译错误“C:\BOOST\BOOST\SPIRIT\home\support\attributes。hpp:1226:错误:无法将'std::basic\u ostream'左值绑定到'std::basic\u ostream&&near'out
我不知道为什么会出现这样的右值错误,我试图为操作添加一个手动重载“因为编译器通常会列出所有可用的
运算符库的候选重载。我试图定义operator@Xander那么,您的问题将是当时操作员不可见。两个原因:它是在相关实例化之后声明的,或者在定义
struct
enum类的命名空间之外声明的。事实上,在我看来,后者很有可能。
#define BOOST_SPIRIT_DEBUG
#include <boost/spirit/include/qi.hpp>
#include <iostream>

namespace qi    = boost::spirit::qi;

struct data_t
{
    std::string label;
    enum Choice { left, right, up, down } choice;

    data_t(std::string label="default", Choice choice=left): label(std::move(label)), choice(choice) {}

    friend std::ostream& operator<<(std::ostream& os, Choice const& v) {
        switch(v) { 
            case left: return os << "left";
            case right:return os << "right";
            case up:   return os << "up";
            case down: return os << "down";
            default:   return os << "?";
        }
    }
    friend std::ostream& operator<<(std::ostream& os, data_t const& v) {
        return os << "{label:" << v.label << ";choice:" << v.choice << "}";
    }
};


template <typename It, typename Skipper = qi::space_type>
    struct parser : qi::grammar<It, data_t(), Skipper>
{
    parser() : parser::base_type(start)
    {
        using namespace qi;

        choice_.add
            ("left",  data_t::left)
            ("right", data_t::right)
            ("up",    data_t::up)
            ("down",  data_t::down);

        start %= as_string[ lexeme[+graph] ] >> lexeme [choice_];

        BOOST_SPIRIT_DEBUG_NODE(start);
    }

private:
    qi::symbols<char, data_t::Choice> choice_;
    qi::rule<It, data_t(), Skipper> start;
};

bool doParse(const std::string& input)
{
    typedef std::string::const_iterator It;
    auto f(begin(input)), l(end(input));

    parser<It, qi::space_type> p;
    data_t data;

    try
    {
        bool ok = qi::phrase_parse(f,l,p,qi::space,data);
        if (ok)   
        {
            std::cout << "parse success\n";
            std::cout << "data: " << data << "\n";
        }
        else      std::cerr << "parse failed: '" << std::string(f,l) << "'\n";

        if (f!=l) std::cerr << "trailing unparsed: '" << std::string(f,l) << "'\n";
        return ok;
    } catch(const qi::expectation_failure<It>& e)
    {
        std::string frag(e.first, e.last);
        std::cerr << e.what() << "'" << frag << "'\n";
    }

    return false;
}

int main()
{
    bool ok = doParse("label1 up");
    return ok? 0 : 255;
}
#define BOOST_SPIRIT_DEBUG
#include <boost/spirit/include/qi.hpp>
#include <iostream>

namespace qi    = boost::spirit::qi;

struct data_t
{
    std::string label;
    enum class Choice { left, right, up, down } choice;

    data_t(std::string label="default", Choice choice=Choice::left): label(std::move(label)), choice(choice) {}

    friend std::ostream& operator<<(std::ostream& os, Choice const& v) {
        switch(v) { 
            case Choice::left: return os << "left";
            case Choice::right:return os << "right";
            case Choice::up:   return os << "up";
            case Choice::down: return os << "down";
            default:   return os << "?";
        }
    }
    friend std::ostream& operator<<(std::ostream& os, data_t const& v) {
        return os << "{label:" << v.label << ";choice:" << v.choice << "}";
    }
};


template <typename It, typename Skipper = qi::space_type>
    struct parser : qi::grammar<It, data_t(), Skipper>
{
    parser() : parser::base_type(start)
    {
        using namespace qi;

        choice_.add
            ("left",  data_t::Choice::left)
            ("right", data_t::Choice::right)
            ("up",    data_t::Choice::up)
            ("down",  data_t::Choice::down);

        start %= as_string[ lexeme[+graph] ] >> lexeme [choice_];

        BOOST_SPIRIT_DEBUG_NODE(start);
    }

private:
    qi::symbols<char, data_t::Choice> choice_;
    qi::rule<It, data_t(), Skipper> start;
};

bool doParse(const std::string& input)
{
    typedef std::string::const_iterator It;
    auto f(begin(input)), l(end(input));

    parser<It, qi::space_type> p;
    data_t data;

    try
    {
        bool ok = qi::phrase_parse(f,l,p,qi::space,data);
        if (ok)   
        {
            std::cout << "parse success\n";
            std::cout << "data: " << data << "\n";
        }
        else      std::cerr << "parse failed: '" << std::string(f,l) << "'\n";

        if (f!=l) std::cerr << "trailing unparsed: '" << std::string(f,l) << "'\n";
        return ok;
    } catch(const qi::expectation_failure<It>& e)
    {
        std::string frag(e.first, e.last);
        std::cerr << e.what() << "'" << frag << "'\n";
    }

    return false;
}

int main()
{
    bool ok = doParse("label1 up");
    return ok? 0 : 255;
}