Сложность: medium
Обобщённая аббревиатура слова может быть построена путём замены несмежных и неперекрывающихся подстрок на их длины.
Например, для слова "abcde" возможны сокращения:
"a3e" — "bcd" заменено на "3"
"1bcd1" — "a" и "e" заменены на "1"
"5" — всё слово заменено на длину
"abcde" — без сокращений
Недопустимы:
"23" — замены "ab" и "cde" смежны
"22de" — замены "ab" и "bc" перекрываются
Нужно вернуть все возможные обобщённые аббревиатуры слова word.
Пример:
Input: word = "a"
Output: ["1","a"]
👨💻 Алгоритм:
1⃣Создание битовых масок
Каждая аббревиатура имеет одно к одному соответствие с n-битным двоичным числом x, где n - длина слова. Используйте эти числа в качестве чертежей для построения соответствующих аббревиатур.
2⃣Генерация аббревиатур
Для числа x просканируйте его бит за битом, чтобы определить, какие символы следует сохранить, а какие - сократить. Если бит равен 1, сохраните соответствующий символ, если 0 - замените его на счетчик.
3⃣Перебор всех комбинаций
Для каждого числа от 0 до 2^n - 1 используйте его битовое представление для создания соответствующей аббревиатуры. Сканируйте число x побитово, извлекая его последний бит с помощью b = x & 1 и сдвигая x вправо на один бит x >>= 1.
😎 Решение:
class Solution {
function generateAbbreviations($word) {
$result = [];
$n = strlen($word);
for ($x = 0; $x < (1 << $n); $x++) {
$result[] = $this->abbr($word, $x);
}
return $result;
}
private function abbr($word, $x) {
$builder = "";
$k = 0;
$n = strlen($word);
for ($i = 0; $i < $n; $i++, $x >>= 1) {
if (($x & 1) == 0) {
if ($k != 0) {
$builder .= $k;
$k = 0;
}
$builder .= $word[$i];
} else {
$k++;
}
}
if ($k != 0) $builder .= $k;
return $builder;
}
}
$sol = new Solution();
print_r($sol->generateAbbreviations("word"));Ставь 👍 и забирай 📚 Базу знаний