====== RegExp Python ======
==== Общее ====
* **match()** - соответствует ли началу строки (либо None)
* **search()** - поиск по всей строке (либо None)
* **findall()** - поиск всех совпадений и возврат в виде списка
* **finditer()** - поиск всех совпадений и возврат их в виде словаря с именем группы
* **sub()** - ищет все совпадения и заменяет указанным значением
* **split()** - разделяет строку по заданному шаблону
:!: Search
Ищет только первое совпадение\\
**match = re.search(regex, string)**\\
Объект **Match** имеет несколько методов, например **group()**, который возвращает части строки сгруппированные в скобки, вернет \\
:!: Объект результата (match)
* **string** - строка .. оО
* **group (groups, groupdict)** - фрагменты, соответствующие шаблону
* **start (end)** - начало/окончание фрагмента
* **pos (endpos)** - начальная/конечная позиции
* **expand** - замена в строке
* **lastindex (lastgroup)** - пар-ры последней группы
:!: Жадность символов повторения
По умолчанию ищет самый большой кусок, можно ограничить вопросительным знаком, например\\
line = ' some text>'
match = re.search(r'<.*>', line)
match.group()
--> ' some text>''
line = ' some text>'
match = re.search(r'<.*?>', line)
match.group()
--> ''
:!: Еще раз про спец символы и повторения
regex+ - одно или более повторений предшествующего элемента
regex* - ноль или более повторений предшествующего элемента
regex? - ноль или одно повторение предшествующего элемента
regex{n} - ровно n повторений предшествующего элемента
regex{n,m} - от n до m повторений предшествующего элемента
regex{n,} - n или более повторений предшествующего элемента
. - любой символ, кроме символа новой строки
^ - начало строки
$ - конец строки
[abc] - любой символ в скобках
[^abc] - любой символ, кроме тех, что в скобках
a|b - элемент a или b
(regex) - выражение рассматривается как один элемент. Кроме того, подстрока, которая совпала с выражением, запоминается
==== Группировка выражений ====
Удобно когда нужно описать подробно строку но извлечь только ее часть\\
:!: Нумерованные группы
Заключена в круглые скобки, группы нумеруются слева на право, начинается с единицы\\
# Обращаться к группам можно по номерам, можно указать несколько номеров
match.group(0)
match.group(1, 2, 1)
# Так тоже можно
match[1]
# Перечислить все группы
match.groups()
:!: Именованные группы
Синтаксис **(?Pregexp)**\\
match.group('name')
# Можно получить словарь где ключи - имена групп
match.groupdict()
:!: Группа без захвата
Если выражение нужно сгруппировать для какой то другой цели, например указать повторение, но в результат выводить не нужно, следует указать в такой группе символ **?:**\\
# Первая группа не будет в выводе, скобки только для указания повторов
re.search(r'((?:\w{4}\.){2}\w{4}).+vlan (\d+).+port (\S+).+port (\S+)', log)
:!: Переиспользование групп в выражении
Значение групп захвата можно подставлять в это же выражение\\
# Как не именованные
re.search(r'(\d+) \1', line)
re.search(r'(\d+) \1 \1', line)
# Так и именованные
re.search(r'(?P\d+) (?P=as)', line)
:!: Поиск по шаблону строки
for read_line in raw_input_log:
# Отсеиваем записи с финишем по файлам
match_line = re.search('.*Thread-\d+ \((?P.*)\.log;.* Finished over (?P\d+) minute.*', read_line)
if match_line:
# Извлекаем текущее имя файла
current_filename = match_line.group('filename')
# Отсекаем старую статистику в имени если она есть
clear_filename = re.sub('^\d+_', '', current_filename)
clear_filename = re.sub('_\d+min$', '', clear_filename)
# Извлекаем длительность файла
duration = match_line.group('duration')
:!: