Разбор задачи: Поиск и замена шаблона

Предложенный нами код:

 def findAndReplacePattern(words, pattern):
        """
        :type words: List[str]
        :type pattern: str
        :rtype: List[str]
        """
        res = []
        for w in words:
            mp12, mp21, match = {}, {}, True
            for c1, c2 in zip(w, pattern):
                if (c1 in mp12 and mp12[c1] != c2) or (c2 in mp21 and mp21[c2] != c1):
                    match = False
                    break
                mp12[c1], mp21[c2] = c2, c1
            if match: res.append(w)
        return res

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

Основная идея:

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

Шаги выполнения:

1. Инициализация пустого списка:

res = []

Мы начинаем с пустого списка res, в который будем добавлять все слова, соответствующие паттерну.

2. Перебор всех слов из списка:

for w in words:

Мы перебираем каждое слово из списка words. Для каждого слова будем проверять, может ли оно быть преобразовано в паттерн.

3. Для каждого слова создаем два словаря:

mp12, mp21, match = {}, {}, True
  • mp12: будет хранить соответствие букв из слова в буквы из паттерна (слева направо).
  • mp21: будет хранить соответствие букв из паттерна в буквы из слова.
  • match: флаг, который изначально устанавливается в True и будет менять свое значение на False, если на каком-то шаге перестановка не будет выполнена корректно.

4. Перебор символов в слове и паттерне:

for c1, c2 in zip(w, pattern):

Используем zip, чтобы одновременно перебирать символы из слова w и паттерна pattern. В каждой итерации переменные c1 и c2 будут хранить текущие символы из слова и паттерна соответственно.

5. Проверка соответствия букв:

if (c1 in mp12 and mp12[c1] != c2) or (c2 in mp21 and mp21[c2] != c1):
    match = False
    break

В этом фрагменте мы проверяем два условия:

  • Если символ c1 уже был сопоставлен с другим символом в паттерне (по записи в mp12), то проверяем, соответствует ли он текущему символу c2. Если не соответствует, устанавливаем match = False и выходим из цикла, потому что дальнейшее сопоставление бессмысленно.
  • Аналогично проверяем символы в другом направлении: если символ c2 в паттерне уже был связан с другим символом из слова, то это несоответствие также приведет к установке match = False.

6. Заполнение словарей:

mp12[c1], mp21[c2] = c2, c1

Если символы соответствуют друг другу, добавляем их в словари:

  • mp12[c1] = c2 — это означает, что символ c1 из слова соответствует символу c2 из паттерна.
  • mp21[c2] = c1 — это означает, что символ c2 из паттерна соответствует символу c1 из слова.

7. Добавление слова в результат:

if match:
    res.append(w)

Если после проверки всех символов из слова и паттерна флаг match остался равным True, то это означает, что слово успешно соответствует паттерну, и мы добавляем его в список res.

8. Возвращение результата:

return res

Возвращаем список слов, которые соответствуют паттерну.

Пример 1:

words = ["abc", "deq", "mee", "aqq", "dkd", "ccc"]
pattern = "abb"
  • Для слова "abc" не существует корректной перестановки для "abb", потому что "a" не может быть связано с двумя разными буквами "b".
  • Для слова "mee" можно провести перестановку: "m" -> "a", "e" -> "b", и получится слово "mee", которое соответствует паттерну "abb".
  • Аналогично для слова "aqq".
  • Результат: ["mee", "aqq"].

Пример 2:

words = ["a", "b", "c"]
pattern = "a"
  • Все слова состоят из одного символа, и каждый символ из паттерна может быть сопоставлен с любым из этих символов. Результат: ["a", "b", "c"].

 



Вы должны Войти или Зарегистрироваться чтобы оставлять комментарии