re.findall дает результаты, отличные от re.search с тем же шаблоном

1

У меня есть str, что я хочу получить подстроку внутри одинарных кавычек ('):

line = "This is a 'car' which has a 'person' in it!"

поэтому я использовал:

name = re.findall("\'(.+?)\'", line)
print(name[0])
print(name[1])

автомобиль
человек

Но когда я пробую этот подход:

pattern = re.compile("\'(.+?)\'")
matches = re.search(pattern, line)
print(matches.group(0))
print(matches.group(1))
# print(matches.group(2))  # <- this produces an error of course

'автомобиль'
автомобиль

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

Итак, чтобы сделать его более конкретным:

  1. В первом случае с findall шаблон возвращает все подстроки, но в последнем случае он возвращает только первую подстроку.
  2. В последнем случае matches.group(0) (что соответствует всему соответствию в соответствии с документацией) отличается от matches.group(1) (что соответствует первой подгруппе в скобках). Это почему?

re.finditer("\'(.+?)\'", line) возвращает объекты соответствия, поэтому он функционирует подобно re.search.

Я знаю, что есть подобный вопрос НАСТОЛЬКО как этот один или этого одного, но они, кажется, не ответить, почему (или, по крайней мере, я не понял).

  • 3
    Вы понимаете, по крайней мере, что re.search находит только первое совпадение?
  • 1
    Согласно инструкции : просмотрите строку, ища первое место, где шаблон регулярного выражения выдает совпадение
Показать ещё 2 комментария
Теги:

2 ответа

2
Лучший ответ

Вы уже прочитали документы и другие ответы, поэтому я дам вам практическое объяснение

Пусть сначала возьмем этот пример отсюда

>>> m = re.match(r"(\w+) (\w+)", "Isaac Newton, physicist")
>>> m.group(0)       # The entire match
'Isaac Newton'
>>> m.group(1)       # The first parenthesized subgroup.
'Isaac'
>>> m.group(2)       # The second parenthesized subgroup.
'Newton'
>>> m.group(1, 2)    # Multiple arguments give us a tuple.
('Isaac', 'Newton')

Если вы заходите на этот сайт, вы найдете переписку с предыдущими обнаружениями

Изображение 174551

группа (0) принимает полное соответствие, группа (1) и группа (2) соответственно представляют собой группу 1 и группу 2 на картинке. Потому что, как сказано здесь, "Match.group([group1,...]) Возвращает одну или несколько подгрупп совпадения. Если есть один аргумент, результат представляет собой одну строку, если есть несколько аргументов, результатом является кортеж с одним элементом для аргумента. Без аргументов group1 по умолчанию равен нулю (возвращается весь матч) "

Теперь вернемся к вашему примеру

Изображение 174551

Как говорят другие с re.search(pattern, line) вы найдете ТОЛЬКО первое вхождение шаблона ["Сканировать строку, ищущую первое место, где шаблон регулярного выражения создает совпадение" как сказано здесь ") и после предыдущего логика вы теперь поймете, почему matches.group(0) выведет полное совпадение и matches.group(1) группу 1. И вы поймете, почему matches.group(2) дает вам ошибку [потому что, как вы можете видеть из на скриншоте нет этой группы 2 для первого появления в этом последнем примере]

1
  1. re.findall возвращает список совпадений (в данном конкретном примере - первые группы совпадений), тогда как re.search возвращает только первое левое совпадение.

    Как указано в документации python ( re.findall):

    Верните все совпадающие совпадения шаблонов в строке, как список строк. Строка сканируется слева направо, а совпадения возвращаются в найденном порядке. Если одна или несколько групп присутствуют в шаблоне, верните список групп; это будет список кортежей, если шаблон имеет более одной группы. В результат включены пустые совпадения.

  2. matches.group(0) дает вам весь фрагмент строки, который соответствует вашему шаблону, поэтому у него есть кавычки, в то время как matches.group(1) дает вам первую подстроку в скобках совпадающего фрагмента, что означает, что она не будет включать кавычки, поскольку они находятся вне круглых скобок. Проверьте документы Match.group() для получения дополнительной информации.

Ещё вопросы

Сообщество Overcoder
Наверх
Меню