Алгоритм поиска расстояния редактирования до всех подстрок

Даны 2 строки s и t. Мне нужно найти для каждой подстроки на s расстоянии редактирования (расстояние Левенштейна) до t. На самом деле мне нужно знать для каждой i позиции в s, каково минимальное расстояние редактирования для всех подстрок, начинающихся с позиции i.

Например:

t = "ab"    
s = "sdabcb"

И мне нужно получить что-то вроде:

{2,1,0,2,2}

Объяснение:

1st position:
distance("ab", "sd") = 4 ( 2*subst )
distance("ab", "sda") = 3( 2*delete + insert )
distance("ab", "sdab") = 2 ( 2 * delete)
distance("ab", "sdabc") = 3 ( 3 * delete)
distance("ab", "sdabcb") = 4 ( 4 * delete)
So, minimum is 2

2nd position:
distance("ab", "da") = 2 (delete + insert)
distance("ab", "dab") = 1 (delete)
distance("ab", "dabc") = 2 (2*delete)
....
So, minimum is 1

3th position:
distance("ab", "ab") = 0
...
minimum is 0

и так далее.

Конечно, я могу использовать алгоритм грубой силы для решения этой задачи. Но есть ли более быстрый алгоритм?

Спасибо за помощь.


person Ivan Bianko    schedule 15.11.2011    source источник
comment
Я знаю, что ваш ответ {2,1,**0,2**,2} неверен, потому что соседние числа могут отличаться не более чем на 1: если есть подстрока s[i..j] с минимальным расстоянием редактирования от k до t, то подстрока s[(i+1)..j] может соответствовать t со стоимостью не более k+1 путем первого редактирования операция вставка s[i] в самом начале строки. В вашем примере для 4-й позиции distance("ab", "b") = 1 (1 вставка) и для 5-й позиции distance("ab", "cb") = 1 (1 подстановка).   -  person j_random_hacker    schedule 16.11.2011


Ответы (2)


Алгоритм Вагнера-Фишера дает ответ на все префиксы «бесплатно».

http://en.wikipedia.org/wiki/Wagner%E2%80%93Fischer_algorithm

Последняя строка матрицы Вагнера-Фишера содержит расстояние редактирования от каждого префикса s до t.

Итак, в качестве первого решения вашей проблемы для каждого i запустите Wagner-Fischer и выберите наименьший элемент в последней строке.

Мне будет любопытно узнать, знает ли кто-нибудь (или сможет ли найти) лучший подход.

person Nemo    schedule 15.11.2011
comment
Спасибо, но я имел в виду это решение как грубую силу ... и я надеюсь, что существует лучшее решение (связанная с временной сложностью). - person Ivan Bianko; 15.11.2011
comment
Сомневаюсь, что кто-то поймет ваш ответ без примера. - person Elmue; 14.06.2016
comment
если вы имеете в виду s и t, упомянутые в вики, последняя строка содержит расстояние редактирования от s до каждого префикса t, а не расстояние от каждого префикса s до t - person mangusta; 12.02.2019

Найти подстроки в заданной строке очень просто. Вы берете обычный алгоритм Левенштейна и немного его изменяете.

ПЕРВЫЙ: вместо того, чтобы заполнять первую строку матрицы 0,1,2,3,4,5, ... вы заполняете ее полностью нулями. (зеленый прямоугольник)

ВТОРОЙ: Затем вы запускаете алгоритм.

ТРЕТЬЕ. Вместо того, чтобы возвращать последнюю ячейку последней строки, вы ищите наименьшее значение в последней строке и возвращаете его. (красный прямоугольник)

Пример: игла: "aba", стог сена: "c abba c" -> результат = 1 (преобразование abba -> aba)

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

Я протестировал это, и он работает.

Это намного быстрее, чем ваше предложение о пошаговом перемещении символа за символом по строке, как вы это делаете в своем вопросе. Вы создаете матрицу только один раз.

person Elmue    schedule 14.06.2016