C++ 如何在模式中使用斜线?

C++ 如何在模式中使用斜线?,c++,boost,boost-spirit,boost-spirit-lex,C++,Boost,Boost Spirit,Boost Spirit Lex,下面的代码可以很好地编译 clang++-std=c++11 test.cpp-o test 但在运行异常时会抛出异常 在抛出的实例后调用terminate 'boost::lexer::运行时错误' what():尚不支持前瞻(“/”) 问题是input和/或regex(第12行和第39行)中的斜杠(/),但我找不到一个解决方案如何正确地转义它。有什么提示吗 #include <string> #include <cstring> #include <boost/

下面的代码可以很好地编译

clang++-std=c++11 test.cpp-o test

但在运行异常时会抛出异常

在抛出的实例后调用terminate 'boost::lexer::运行时错误' what():尚不支持前瞻(“/”)

问题是input和/或regex(第12行和第39行)中的斜杠(/),但我找不到一个解决方案如何正确地转义它。有什么提示吗

#include <string>
#include <cstring>
#include <boost/spirit/include/lex.hpp>
#include <boost/spirit/include/lex_lexertl.hpp>
#include <boost/spirit/include/qi.hpp>
#include <boost/spirit/include/phoenix.hpp>

namespace lex        = boost::spirit::lex;
namespace qi         = boost::spirit::qi;
namespace phoenix    = boost::phoenix;

std::string regex("FOO/BAR");

template <typename Type>
struct Lexer : boost::spirit::lex::lexer<Type> {
    Lexer() : foobar_(regex) {
        this->self.add(foobar_);
    }
    boost::spirit::lex::token_def<std::string> foobar_;
};

template <typename Iterator, typename Def>
struct Grammar
  : qi::grammar <Iterator, qi::in_state_skipper<Def> > {
    template <typename Lexer> Grammar(const Lexer & _lexer);
    typedef qi::in_state_skipper<Def> Skipper;
    qi::rule<Iterator, Skipper> rule_;
};
template <typename Iterator, typename Def>
template <typename Lexer>
Grammar<Iterator, Def>::Grammar(const Lexer & _lexer)
  : Grammar::base_type(rule_) {
    rule_ = _lexer.foobar_;
}

int main() {
    // INPUT
    char const * first("FOO/BAR");
    char const * last(first + strlen(first));

    // LEXER
    typedef lex::lexertl::token<const char *> Token;
    typedef lex::lexertl::lexer<Token> Type;
    Lexer<Type> l;

    // GRAMMAR
    typedef Lexer<Type>::iterator_type Iterator;
    typedef Lexer<Type>::lexer_def Def;
    Grammar<Iterator, Def> g(l);

    // PARSE
    bool ok = lex::tokenize_and_phrase_parse (
        first
      , last
      , l
      , g
      , qi::in_state("WS")[l.self]
    );

    // CHECK
    if (!ok || first != last) {
        std::cout << "Failed parsing input file" << std::endl;
        return 1;
    }
    return 0;
}
#包括
#包括
#包括
#包括
#包括
#包括
名称空间lex=boost::spirit::lex;
名称空间qi=boost::spirit::qi;
名称空间phoenix=boost::phoenix;
std::字符串正则表达式(“FOO/BAR”);
模板
结构Lexer:boost::spirit::lex::Lexer{
Lexer():foobar(regex){
此->self.add(foobar);
}
boost::spirit::lex::token\u def foobar;
};
模板
结构语法
:qi::语法{
模板语法(const-Lexer&u-Lexer);
typedef qi::处于“状态”的船长;
qi::规则uu;
};
模板
模板
语法::语法(常量词法和u词法)
:语法::基本类型(规则){
规则=\u lexer.foobar;
}
int main(){
//输入
字符常量*第一(“FOO/BAR”);
字符常量*last(first+strlen(first));
//雷克瑟
typedef-lex::lexertl::令牌;
typedef-lex::lexertl::lexer-Type;
Lexer l;
//文法
typedef-Lexer::迭代器\ u型迭代器;
typedef Lexer::lexeru def;
语法g(l);
//解析
bool ok=lex::标记化和短语解析(
第一
,最后
L
G
,qi::在美国(“WS”)[l.self]
);
//检查
如果(!ok | | first!=last){
std::cout作为,
/
很可能被用作先行运算符,很可能是后面的运算符。不幸的是,Spirit不会使用更多的运算符(我并不认为其他语法更优雅;它只是与正则表达式语法中的所有细微变化混淆)

如果您查看
re\u tokeniser.hpp

// Not an escape sequence and not inside a string, so
// check for meta characters.
switch (ch_)
{
    ...
    case '/':
        throw runtime_error("Lookahead ('/') is not supported yet.");
        break;
    ...
}
它认为您不在转义序列中,也不在字符串中,因此它正在检查元字符。
/
被认为是用于前瞻的元字符(即使该功能未实现),并且必须转义

尝试用反斜杠转义
/
(不在输入中)(即
“\\/”
,或
“\/”
,如果使用原始字符串)。或者

我认为这是精神LeX文档中的一个bug,因为它没有指出<代码> /<代码>必须被转义。



编辑:感谢和,他帮助纠正了我以前的一些想法。如果他们在这里发布答案,请确保给他们一个+1。

我尝试用“\\/”、“\/”和“[]”来逃避斜杠。没有解决方案。但是,它失败了,出现了另一个错误。(特别是:
断言失败:(std::size\u t(~0)!=state),函数集\u lexer\u state,文件/usr/local/include/boost/spirit/home/lex/qi/state\u switcher.hpp,第87行。
)。我不太了解Spirit,但听起来你的lexer/parser中有另一个问题。这个答案对于解决斜杠问题应该是正确的。对于另一个问题…我不确定该说什么。这不是有序的选择。还提到PEG规范符号是一个转移视线的问题,因为我们这里没有指定语法。我们是spe指定令牌模式。它们使用正则表达式的子集:(顺便说一句,这是错误消息所建议的)@cornstales新的错误是由于“WS”状态不存在,船长尝试使用它。尝试添加所述状态,似乎有效。@sehe我也不知道,但一点谷歌搜索让我认为错误是指Spirit。Lex不支持flex。我要说的是简化它,这样它就可以在没有
/
的情况下工作了(即,让它只读取和解析
FOOBAR
)。然后,一旦您开始工作,请尝试将
/
添加回。