Нахождение групп подобных строк в большом наборе строк

У меня есть довольно большой набор строк (скажите 100), который имеет много подгрупп, характеризуемых их подобием. Я пытаюсь найти/разработать алгоритм, который нашел бы группы тезисов обоснованно эффективно.

Как пример скажем, входной список слева ниже, и выходные группы справа.

Input                           Output
-----------------               -----------------
Jane Doe                        Mr Philip Roberts
Mr Philip Roberts               Phil Roberts     
Foo McBar                       Philip Roberts   
David Jones                     
Phil Roberts                    Foo McBar        
Davey Jones            =>         
John Smith                      David Jones      
Philip Roberts                  Dave Jones       
Dave Jones                      Davey Jones      
Jonny Smith                     
                                Jane Doe         

                                John Smith       
                                Jonny Smith 

Кто-либо знает о каких-либо способах решить это обоснованно эффективно?

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

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

У кого-либо есть какие-либо мысли/указатели?


ОБНОВЛЕНИЕ: @Will A: Возможно, имена не были столь же хорошим примером, как я сначала думал. Как начальная точка я думаю, что могу предположить, что в данных я буду работать с, небольшое изменение в строке не заставит их спрыгнуть с одной группы другому.

41
задан latentflip 25 July 2010 в 13:25
поделиться

4 ответа

Другой популярный метод - ассоциировать строки по их индексу Жаккара. Начните с http://en.wikipedia.org/wiki/Jaccard_index.

Вот статья об использовании Jaccard-индекса (и пары других методов) для решения проблемы, подобной вашей:

http://matpalm.com/resemblance/

21
ответ дан 27 November 2019 в 00:56
поделиться

Для приведенного вами примера, я считаю, что расстояние Левенштейна было бы неподходящим, поскольку «Бонни Смит» была бы «очень похожа» на «Джонни Смита» и почти наверняка попала бы в то же класс.

Я думаю, вам нужно подойти к этому (при работе с именами) с точки зрения некоторых имен, имеющих синонимы (например, «Джон», «Джон», «Джонни», «Джонни» и т. Д.) И соответствия на основе этих.

1
ответ дан 27 November 2019 в 00:56
поделиться

Проблема, которую вы пытаетесь решить, - это типичная проблема кластеризации .

Начните с простого алгоритма K-средних и используйте расстояние Левенштейна как функцию для вычисления расстояния между элементами и центрами кластеров.

Кстати, алгоритм вычисления расстояния Левенштейна реализован в Apache Commons StringUtils - StringUtils.getLevenshteinDistance

Основная проблема K-Means заключается в том, что вы должны указать количество кластеров (подгрупп в ваших терминах). Итак, у вас будет 2 варианта: улучшить K-средние с помощью некоторой эвристики или использовать другой алгоритм кластеризации, который не требует указания количества кластеров (но этот алгоритм может показать худшую производительность и может быть очень сложным в реализации, если вы решите его реализовать. себя).

6
ответ дан 27 November 2019 в 00:56
поделиться

Если мы говорим о реально произносимых словах, то сравнение (начала) их метафоры может быть полезным:

MRFLPRBRTS: Mr Philip Roberts
FLRBRTS: Phil Roberts   
FLPRBRTS: Philip Roberts 
FMKBR: Foo McBar      
TFTJNS: David Jones    
TFJNS: Dave Jones     
TFJNS: Davey Jones    
JNT: Jane Doe       
JNSM0: John Smith     
JNSM0: Jonny Smith
3
ответ дан 27 November 2019 в 00:56
поделиться
Другие вопросы по тегам:

Похожие вопросы: