Регулярное выражение в ruby для строк с несколькими шаблонами
У меня есть строка с необязательными подстроками, и я искал / работал / для регулярного выражения с захватами имен, единственное регулярное выражение для всех, если это возможно.
в рублях
Пожалуйста помоги,
образцы строк:
string1 = bike wash #a simple task
string2 = bike wash @ bike point # a simple task with location
string3 = bike wash @ bike point on 13 may 11 # task with location and date
string4 = bike wash @ bike point on 13 may 11 @ 10 AM # task with location, date and time
string5 = bike wash on 13 may 11 @ 10 AM # task with date and time without location
string6 = bike wash on 13 may 11 # task and date
Я провел почти день в Google и Stackru, чтобы получить единственное регулярное выражение для всех вышеупомянутых шаблонов строк.
2 ответа
Предположения:
- Место и время начинаются с
@
, а также@
больше нигде не появляется. - Дата начинается с
on
окружены обязательными белыми пространствами, иon
больше нигде не появляется. - Задача обязательна.
- Место и дата не являются обязательными и не зависят друг от друга.
- Время появляется только тогда, когда есть дата.
- Задача, местоположение, дата, время отображаются только в этом порядке.
Кроме того, следует считать само собой разумеющимся, что механизм регулярных выражений является oniguruma, так как упоминается именованный захват.
regex = /
(?<task>.*?)
(?:\s*@\s*(?<location>.*?))?
(?:\s+on\s+(?<date>.*?)
(?:\s*@\s*(?<time>.*))?
)?
\z/x
string4.match(regex)
# => #<MatchData
"bike wash @ bike point on 13 may 11 @ 10 AM"
task: "bike wash"
location: "bike point"
date: "13 may 11"
time: "10 AM"
>
Чтобы регулярное выражение выполняло эту работу, необходимо сделать некоторые предположения. Задачи не должны включать " @ " или "вкл", например, но их может быть больше.
Чтобы соответствовать любому символу, кроме первого пробела для " @ " или "вкл", я бы использовал (?! @ | on ).
Таким образом, вы можете найти задачу, используя (((?! @ | on ).)+)
, Затем следует необязательное местоположение с префиксом " @ ": (?: @ ((?:(?! on ).)+))?
, Обратите внимание, что местоположение не должно включать "вкл" здесь.
После этого есть дополнительная дата с дополнительным временем: (?: on ((?:(?! @ ).)+)(?: @ (.+))?)?
, Все вместе:
((?:(?! @ | on ).)+)(?: @ ((?:(?! on ).)+))?(?: on ((?:(?! @ ).)+)(?: @ (.+))?)?
Это будет иметь задачу, местоположение, дату и время в первых четырех группах захвата. Смотрите здесь: http://regexr.com/?2tnb3