Регулярное выражение — «захваченная группа равна» в условии

#regex #date

#регулярное выражение #Дата

Вопрос:

Я пишу регулярное выражение для захвата различных форматов даты. Чтобы сделать его коротким и гибким, я хотел упаковать все возможные комбинации месяцев, дней и лет в отдельные группы. Предположим, у меня есть две такие даты:

01.01. — 31.12.2013

январь — декабрь 2013

Теперь, чего я хочу добиться, это написать регулярное выражение, которое будет фиксировать обе даты, подобные указанным выше. это просто. но я также хочу исключить такие даты, как, например, те:

01.01. — 31 декабря 2013

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

Я хотел создать условие, которое фиксирует только соответствующие поля второй даты, основываясь на том, что найдено в первом (так, например, если первая дата имеет альфа-месяц, ищите только альфа-месяц во втором, игнорируйте числовой). Мое регулярное выражение выглядит так:

 (?<firstDay>0[1-9]|[12][0-9]|3[01]|[1-9])[-/s.](?<firstMonth>0[1-9]|1[012]|[p{L}]{3,}|[1-9])s*[-s/.]*s*(?<secondDay>0[1-9]|[12][0-9]|3[01]|[1-9])[-s/.]*(?<secondMonth>((?<firstMonth>)(?<=0[1-9]|1[012]|[1-9]))(0[1-9]|1[012]|[1-9])|[p{L}]{3,})[-s/.]*(?<year>(19|20)dd|[012][0-9]$)
 

Это все предыстория, но мой вопрос в том, можно ли проверить, чему равна захваченная группа, и на основе этого создать условие захвата?Я нашел похожую тему о переполнении стека (к сожалению, не могу найти ее сейчас для ссылки), но когда я ее реализую, она перестает фиксировать некоторые правильные даты (например, 01.01. — 31.12.2013). Это та часть:

 (?<secondMonth>((?<firstMonth>)(?<=0[1-9]|1[012]|[1-9]))(0[1-9]|1[012]|[1-9])|[p{L}]{3,})
 

Комментарии:

1. Какой тип регулярных выражений вы используете? Какой язык? Например, Perl имеет такой приятный синтаксис: (?(condition)yes-pattern|no-pattern)

2. Я делаю это на C #. Синтаксис, который вы предлагаете, в порядке, но как мне написать часть «условие»? Я знаю только о возможности проверить, идентифицирована ли группа или нет, но не о том, какое значение она принимает.

3. .Net поддерживает этот синтаксис, так что все в порядке. Я не до конца обдумал это, поскольку не дал полного ответа, но вы могли бы поместить каждую альтернативу в группе firstMonth захвата в свою собственную группу захвата, таким образом, вы можете узнать, какая альтернатива соответствует. (?<firstMonth>(?<firstMonthNumeric>...)|(?<firstMonthName>...))

4. Вторая мысль: я думаю, вы должны сопоставлять все свободно, используя регулярные выражения, а затем отфильтровывать плохие результаты в коде, используя match.Groups[...] , чтобы проверить, какая группа соответствует. Это будет намного проще.

5. Нет, при разнообразии возможных форматов дат это очень негибко 🙂 Кроме того, у меня есть ссылки на именованные группы в коде C #.