Название: Сохранить вложенную "константу строки" в RegExp Отправлено: Гурман от Август 20, 2019, 12:54 Нужен разбор строки аналогичный QStringList parts = entire.split(QRegExp("\\W+"), QString::SkipEmptyParts);, но чтобы если в ней встречается последовательность символов между двойных кавычек, она целиком и без кавычек переносилась в элемент List-а. То есть, если есть строка:
Мама, глядя, сказала: "твою мать"\n и ушла. Она разбиралась на Мама глядя сказала твою мать и ушла То есть, строка эта изначально в QString (не строковая константа в коде), а \n - символ перевода каретки внутри неё. Может у кого-нибудь в коллекции есть такое? В кладовой готовых я не нашёл, гугл выдаёт всякую хрень. Название: Re: Сохранить вложенную "константу строки" в RegExp Отправлено: m_ax от Август 20, 2019, 14:48 Цитировать В кладовой готовых я не нашёл, гугл выдаёт всякую хрень. Плохо искали) Помню, одно время эта тема горячо обсуждалась) И решений было несколько предложено) http://www.prog.org.ru/topic_22338_0.html (http://www.prog.org.ru/topic_22338_0.html)А вообще для этого есть boost::tokenizer https://www.boost.org/doc/libs/1_66_0/libs/tokenizer/ (https://www.boost.org/doc/libs/1_66_0/libs/tokenizer/) Код
Название: Re: Сохранить вложенную "константу строки" в RegExp Отправлено: Гурман от Август 20, 2019, 22:11 Цитировать В кладовой готовых я не нашёл, гугл выдаёт всякую хрень. Плохо искали) Помню, одно время эта тема горячо обсуждалась) И решений было несколько предложено) http://www.prog.org.ru/topic_22338_0.html (http://www.prog.org.ru/topic_22338_0.html)А вообще для этого есть boost::tokenizer https://www.boost.org/doc/libs/1_66_0/libs/tokenizer/ (https://www.boost.org/doc/libs/1_66_0/libs/tokenizer/) Просмотрел, там много воды и нет явного подходящего варианта. Много лишнего, задача немного другая, немного проще - в строке цельные токены выделяются только кавычками. Ковырять и экспериментировать мне некогда. Boost и std:string не подходят, у меня их нет в приложении вообще, оно делается для Android. Сейчас пока на GNU CC, потом для выпуска перейду на Clang - там родное Qt-шное гарантированно работает, а с посторонними библиотеками и тулзами не известно. Поэтому только QString и собственные библиотеки Qt5. Название: Re: Сохранить вложенную "константу строки" в RegExp Отправлено: Igors от Август 21, 2019, 08:55 А вообще для этого есть boost::tokenizer Пример ниже дает такой выхлопЦитировать Мама Т.е. он рубит по запятым. Ладно, добавил пробел во второй аргументглядя сказала твою мать и ушла Код: escaped_list_separator<char> sep("\\", " :,", "\""); Цитировать Мама Чего он насовал пустых строк?глядя сказала твою мать и ушла И еще: поменял \n на \r (есть такие старые текстовики) Код: std::string s = "Мама, глядя, сказала: \"твою мать\" \\r и ушла"; Ну и дока, как всегда, полный отстой. Приводят пример - та покажите что он печатает - ни фига. В общем, не все так радужно как говорят фаны дуста :) Название: Re: Сохранить вложенную "константу строки" в RegExp Отправлено: m_ax от Август 21, 2019, 12:38 Цитировать В общем, не все так радужно как говорят фаны дуста :) Я уже не однократно говорил в цитируемой выше теме, что главным преимуществом tokenizer является его расширяемость.И также, в той теме, я привёл пример, как переопределив TokenFunction (один из шаблонов tokenizerа) можно добиться любого поведения. Я бы предложил TC, на основе архитектуры boost::tokenizer, написать свой класс QTokenizer. Думаю, это работа на пару вечеров. Название: Re: Сохранить вложенную "константу строки" в RegExp Отправлено: Гурман от Август 21, 2019, 15:21 Я бы предложил TC, на основе архитектуры boost::tokenizer, написать свой класс QTokenizer. Думаю, это работа на пару вечеров. Когда-нибудь в другой раз. Мне меньше чем за 10 дней до отъезда надо кучу всего сделать. Поскольку решение быстро не было найдено, пришлось изменить спецификации - разрешить в строке простые тэги и быстро сделать разбор строки по ним. За полдня. Так что вопрос пока снимается. Но вообще писание самих регэкспов достаточно муторное занятие, интересно было бы иметь что-то вроде "библиотеки" из них. Публичной, разумеется. Чтобы в ней можно было найти готовое решение для своей задачи, или хотя бы с минимальной корректировкой, возможностью тут же онлайн проверить вводом тестовой строки.Может быть такое уже и есть, но я не нашёл. Название: Re: Сохранить вложенную "константу строки" в RegExp Отправлено: Igors от Август 21, 2019, 17:32 Я уже не однократно говорил в цитируемой выше теме, что главным преимуществом tokenizer является его расширяемость. Это там где имена "bra" и "ket"? (больше ничего не помню :)). Ну ладно, попробуем, как говорится, "конструктивно". Вот добавили пробел как символ-разделитель, и Ваш пример "почти работает", но есть бяка - пустые строки. Причем почему-то между "и" и "ушла" пустышки нет. Как от них избавиться? Ладно, еще читаем доку, глядим в исходники - ага, если больше одного разделителя, он выдает остальные "на гора" (неудобно сделано). Причем для char_separator есть traits чтобы это подавить, а вот для escaped_list_separator нема :'( И также, в той теме, я привёл пример, как переопределив TokenFunction (один из шаблонов tokenizerа) можно добиться любого поведения. А время-то идет. И как решать с пустышками - хз. Наверное придется предъявить "testimonium paupertatis" и фильтровать на выходе. Ото и вся "расширяемость" - сломалась на первом скачке. Или я неправ? Я бы предложил TC, на основе архитектуры boost::tokenizer, написать свой класс QTokenizer. Думаю, это работа на пару вечеров. Если ничего больше не надо кроме "текст в кавычках" (т.е. нет скобок, вложенности, экранированных кавычек и.т.п.) - то написать с нуля, чисто на QString... ну минут 15, какие там "пару вечеров" :) Ну хорошо, допустим подсчет затраченного времени = фигня (хотя я так не считаю), зато "на основе архитектуры" - это будет круто, не то что там какой-то велик (ну мы же читали/изучали, зря что ли?). И опять-таки не могу согласиться. Откройте тот же escaped_list_separator - там же ничего нет, та же студенческая лаба, только с задроченым сынтаксысом. Это слишком бедная основа чтобы на ней что-то развивать. Название: Re: Сохранить вложенную "константу строки" в RegExp Отправлено: kambala от Август 21, 2019, 19:23 Код: (?<=").+(?=")|\b\w+\b проверил на свифте: Код: import Foundation Название: Re: Сохранить вложенную "константу строки" в RegExp Отправлено: Igors от Август 22, 2019, 05:07 Еще копнем boost::tokenizer, попробуем вложенные кавычки
Код: int main() Цитировать str1 И опять проблемы, и опять как их решать - хз. str2 str3 str4 str5 str6 Название: Re: Сохранить вложенную "константу строки" в RegExp Отправлено: m_ax от Август 22, 2019, 11:29 Цитировать И опять проблемы, и опять как их решать - хз. Да, escaped_list_separator, возможно, представляет не самое продуманное решение. Но что мешает дополнить tokenizer своим spec_char_separator'ом? Который будет и множественные и вложенные цитаты учитывать, и токены различные и т.д. и т.п. При этом в той теме (Разбор QString) я уже выкладывал такое решение. Выложу ещё раз) Код
Вывод: Код
Приаттачиваю проектик. Название: Re: Сохранить вложенную "константу строки" в RegExp Отправлено: Igors от Август 22, 2019, 14:41 При этом в той теме (Разбор QString) я уже выкладывал такое решение. Выложу ещё раз) За проект спасибо, разрывать старье было бы чижело. Однако проект - вовсе не main что Вы процитировали - содержательная часть там в хедере, строк 240 - не так уж мало, и код не так уж очевиден. ... Приаттачиваю проектик. Тогда возникает законный вопрос - а что это за инструментарий такой (tokenizer) если для достижения даже относительно простого ф-ционала уже нужно наклепать не одну сотню строк? Ведь решение "с нуля" отнюдь не длиннее. Заметим что если наращивать ф-ционал - то опять все руками, напр Цитировать std::string str = "str1 'str2 \"str3' str4\" str5' str6"; Это сейчас не работает, нет приоритета кавычек. Потребуется добавить - опять все на Вас. Тогда зачем брать tokenizer за основу? Что Вы с него имеете? Концепцию токенов? Ну QStringRef в этом плане никак не хуже. Что еще? Навязанный call оператор ()? Так это в минус.Название: Re: Сохранить вложенную "константу строки" в RegExp Отправлено: m_ax от Август 22, 2019, 14:56 Цитировать содержательная часть там в хедере, строк 240 - не так уж мало, и код не так уж очевиден. Ну не 240 строк.. Последний класс quote_extractor (Вот Вам другой пример поведения токенайзера, когда токены - это содержимое цитат) не нужен для Вашего примера.Вся содержательная часть содержится как раз в теле оператора operator()() где меньше 50 строк кода. Цитировать Тогда возникает законный вопрос - а что это за инструментарий такой (tokenizer) если для достижения даже относительно простого ф-ционала уже нужно наклепать не одну сотню строк? В расширяемости, без изменения его интерфейса. Вы можете написать множество (для разных узких специализаций) вариантов разбиения на токены. И это архитектурно правильный подход, чем писать на каждый случай новый парсер. Мы же об этом уже 100500 раз спорили в той теме) Цитировать Это сейчас не работает, нет приоритета кавычек. Приоритет кавычек - это вообще отдельная песня.. Мы это тоже обсуждали, если помните) И что я об этом думаю, можете также найти в известной теме)) Название: Re: Сохранить вложенную "константу строки" в RegExp Отправлено: Igors от Август 23, 2019, 03:59 Вся содержательная часть содержится как раз в теле оператора operator()() где меньше 50 строк кода. Ну если вызываемые утилиты не считать.. :)В расширяемости, без изменения его интерфейса. Вы можете написать множество (для разных узких специализаций) вариантов разбиения на токены. В том что "растительное масло без холестерина" никакой дустовской заслуги нет :) Возобновлять старый спор нет смысла т.к. рез-т давно известен :) Поговорим о другомИ это архитектурно правильный подход, чем писать на каждый случай новый парсер. Мы же об этом уже 100500 раз спорили в той теме) А вообще: нужно ли "множество вариантов разбиения на токены"? Вот популярная хотелка Цитировать 21.32 Как получить токен-флот? Можно просто забить на точку, плюс и минус и попробовать конвертнуть строку - пройдет или нет. Но тогда лишаемся такой возможности2.12e+4 2.1e-5f Цитировать 2+2 Наверное лучше все-таки плюс ловить. Тогда что - менять нутро "разбивщика"? Добавлять ему еще опции? Но это никакая не "расширяемость"Думается правильно сделать еще класс (layer) который принимает "сырые" токены базового, и как-то их группирует Название: Re: Сохранить вложенную "константу строки" в RegExp Отправлено: m_ax от Август 23, 2019, 11:38 Цитировать Вот популярная хотелка Да чтож это за мания у Вас такая: из всего своять супер класс) ... Как получить токен-флот? Можно просто забить на точку, плюс и минус и попробовать конвертнуть строку - пройдет или нет. Но тогда лишаемся такой возможности Умеете утюг - замечательно, но будет немного дико с его помощью решать все проблемы :) Токенайзер решает узкий круг специальных задач. Он расширяем, производителен и простой. Всё. Хотите большего, ищите соответствующий инструментарий. Название: Re: Сохранить вложенную "константу строки" в RegExp Отправлено: Гурман от Август 24, 2019, 14:33 тогда лишаемся такой возможности Эта хотелка давно и просто делается рекурсивным разбором выражений. Описано в любом учебнике по компиляторам. Можно просто тупо брать ветку БНФ из языка Си, и реализовывать. Разумеется, таким же разбором можно и кавычки и любые скобки разбирать без всяких RegExp, но в реальном приложении это будет стрельба из пушки по воробьям.Цитировать 2+2 Название: Re: Сохранить вложенную "константу строки" в RegExp Отправлено: Igors от Август 24, 2019, 15:00 Он расширяем, производителен ... Философия (дустовского) сачка не заслуживает обсуждения :)Цитировать double test = 1.3e+2+5; Это свинство компилится, test = 135. Хммм... как же его цивильно (без хардкодинга) распарсить ?Название: Re: Сохранить вложенную "константу строки" в RegExp Отправлено: m_ax от Август 24, 2019, 16:41 Я не понял, это Вы к чему?)
Название: Re: Сохранить вложенную "константу строки" в RegExp Отправлено: Igors от Август 25, 2019, 10:05 Я не понял, это Вы к чему?) Ну обдумываю как "я бы делал" парсер арифметики/интерпретатора. Это не значит что мне он "срочно нужен" (пока вообще не нужен). Но если понадобится - там уже думать/обсуждать будет некогда, придется чего-то искать/хватать. В общем, "на будущее". |