Не могу решить задачу на регулярное выражение

Рейтинг: 1Ответов: 1Опубликовано: 08.02.2023

Новичок в регулярных выражениях, более-менее лёгкие задачи получаются, эта вообще не выходит. Задача - удалить из строки все повторяющиеся слова, оставив только одиночные (первые) слова (не меняя порядок слов). Пример

введите сюда описание изображения

import re
def remove_duplicate_words(s):
    pattern=r''
    return re.sub(pattern,'', s)
print(remove_duplicate_words("alpha beta beta gamma gamma gamma delta alpha beta beta gamma gamma gamma delta"))
print(remove_duplicate_words("my cat is my cat fat"))

Ответы

▲ 2Принят

С помощью re ничего не выйдет, так как чтобы оставить первые вхождения повторяющихся слов нужна поддержка блока предварительного просмотра назад неограниченной длины. Такая поддержка имеется в PyPi regex:

import regex

def remove_duplicate_words(s):
    pattern=r'\b(\w+)\b(?<=\b\1\b.*\1)\s*'
    return regex.sub(pattern,'', s)

print(remove_duplicate_words("alpha beta beta gamma gamma gamma delta alpha beta beta gamma gamma gamma delta"))  # => alpha beta gamma delta 
print(remove_duplicate_words("my cat is my cat fat")) # => my cat is fat

См. пример работы кода.

Подробности

  • \b - граница слова
  • (\w+) - Группа №1: одна и более букв, цифр или символов нижнего подчёркивания
  • \b - граница слова
  • (?<=\b\1\b.*\1) - блок предварительного просмотра назад, который отменяет совпадение, если сразу перед текущей позицией имеется
    • \b\1\b - значение первой группы как целое слово
    • .* - ноль и более символов, отличных от символов перевода строки, как можно больше
    • \1 - текст, захваченные первой группой (\1 здесь необходим, так как блок находится после \b(\w+)\b)
  • \s* - ноль и более пробельных символов.