私は単純な構造を持っています
// in namespace client
struct UnaryExpression
{
std::string key;
SomeEnums::CompareType op;
};
SomeEnums::CompareType
は、シンボルテーブルを次のように定義する列挙型です。
struct UnaryOps : bsq::symbols<char, SomeEnums::CompareType>
{
UnaryOps() : bsq::symbols<char, SomeEnums::CompareType>(std::string("UnaryOps"))
{
add("exists", SomeEnums::Exists)
("nexists", SomeEnums::NotExists);
}
};
私は構造体を解析したい2つの異なる方法を持っています.別のスレッドで尋ねて、(ほとんど)動作するようになりました.
私の文法は次のようになります。
template<typename Iterator>
struct test_parser : bsq::grammar<Iterator, client::UnaryExpression(), bsq::ascii::space_type>
{
test_parser()
: test_parser::base_type(unaryExp, std::string("Test"))
{
using bsq::no_case;
key %= bsq::lexeme[bsq::alnum >> +(bsq::alnum | bsq::char_('.'))];
unaryExp %= unaryE | unaryF;
unaryE %= key >> no_case[unaryOps];
unaryF %= no_case[unaryOps] >> '(' >> key >> ')';
};
UnaryOps unaryOps;
bsq::rule<Iterator, std::string(), bsq::ascii::space_type> key;
bsq::rule<Iterator, client::UnaryExpression(), bsq::ascii::space_type> unaryExp;
bsq::rule<Iterator, client::UnaryExpression(), bsq::ascii::space_type> unaryE;
bsq::rule<Iterator, client::UnaryFunction(), bsq::ascii::space_type> unaryF;
};
そして、次のロジックを使用してコードを解析しています。
bool r = phrase_parse(iter, end, parser, bsq::ascii::space, exp);
if (r && iter == end)
{
std::cout << "-------------------------\n";
std::cout << "Parsing succeeded\n";
std::cout << "key: " << exp.key << "\n";
std::cout << "op : " << exp.op << "\n";
std::cout << "-------------------------\n";
}
これは、入力を次のようにfoo exists
行い、exp.key が「foo」に等しく、exp.op が対応する列挙値 (この場合は 0) に等しい場合、すべて正常に機能します。のようなものfoo1 nexists
も機能します。
ただし、その 2 番目のルールは、期待どおりには機能しません。入力を与えるとnexists(foo)
、次の出力が得られます。
-------------------------
Parsing succeeded
key: nexistsfoo
op : 1
-------------------------
列挙値が適切に設定されているようですが、「nexts」がキー文字列の前に追加されている理由がわかりません。キーが2番目のルールで「foo」と等しくなるようにルールを修正する方法を教えてください。
ここに私の問題を説明する削除されたコードのコピーを投稿しました: http://pastebin.com/402M9iTS