Boost Spirit X3 Пропустить реализацию парсера?

Для текущей грамматики, которую я анализирую с помощью X3, пробелы и комментарии в стиле Perl игнорируются.

Мне кажется, что парсер пропуска в X3 - это просто обычный парсер, и любой ввод, который он потребляет, считается «пропущенным». Я придумал это:

namespace x3 = boost::spirit::x3;
auto const blank_comment = 
   x3::blank | x3::lexeme[ '#' >> *(x3::char_ - x3::eol) >> x3::eol ];

При анализе очень простого ввода (пара строк комментариев и одна строка строки в кавычках) это, похоже, работает хорошо. (Живите на Coliru)

Однако, поскольку я не могу найти никакой документации по этому вопросу, а детали текущих парсеров пропуска спрятаны в сложной системе шаблонов, я надеялся на некоторый ввод.

  1. Это правильный способ определения "парсера пропуска"? Есть стандартный метод?
  2. Есть ли проблемы с производительностью при такой реализации? Как бы это было улучшено?

Я ранее искал подробности в SO и нашел ответ с помощью Qi (Custom Skip Parser with Boost :: Дух). Поскольку я никогда не изучал Ци, многие детали трудно понять. Описанный выше метод кажется более интуитивным.


person Zac    schedule 09.02.2016    source источник


Ответы (1)


Да это нормально.

Шкипер кажется довольно оптимальным. Вы можете оптимизировать правило quoted_string, переупорядочив и используя отрицание набора символов (operator~):

Live On Coliru

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

namespace parser {
    namespace x3 = boost::spirit::x3;
    auto const quoted_string = x3::lexeme [ '"' >>  *('\\' >> x3::char_ | ~x3::char_("\"\n")) >> '"' ];
    auto const space_comment = x3::space | x3::lexeme[ '#' >> *(x3::char_ - x3::eol) >> x3::eol];
}

#include <iostream>
int main() {
    std::string result, s1 = "# foo\n\n#bar\n   \t\"This is a simple string, containing \\\"escaped quotes\\\"\"";

    phrase_parse(s1.begin(), s1.end(), parser::quoted_string, parser::space_comment, result);

    std::cout << "Original: `" << s1 << "`\nResult: `" << result << "`\n";
}

Печать

Original: `# foo

#bar
    "This is a simple string, containing \"escaped quotes\""`
Result: `This is a simple string, containing "escaped quotes"`
person sehe    schedule 10.02.2016
comment
Спасибо за совет по оптимизации и ответ. - person Zac; 10.02.2016
comment
Возможно, для space_comment лучше использовать директива seek? - person Tomilov Anatoliy; 11.02.2016
comment
@Orient Я не рекомендую в зависимости от неподдерживаемого участника упрекнуть в чем-то, что очень похоже на преждевременную оптимизацию. - person sehe; 11.02.2016
comment
Ok. Телефоны сложны в использовании. Я не рекомендую полагаться на неподдерживаемый код участника для ... - person sehe; 11.02.2016
comment
Репозиторий содержит код плохого качества? Я предлагаю это выше не для оптимизации, а для удобства чтения. - person Tomilov Anatoliy; 11.02.2016
comment
Неплохой код. Это просто не поддерживается. Документы довольно четко об этом говорят. Я сильно подозреваю, что здесь ничуть не лучше. - person sehe; 11.02.2016
comment
Кстати, директива поиска является частью основного кода Spirit X3. Я только что связал соответствующую документацию из репозитория Spirit V2. - person Tomilov Anatoliy; 17.02.2016