Сложная проблема сортировки - какой тип алгоритма мне использовать? - PullRequest
3 голосов
/ 15 апреля 2011

Проблема:

N узлов связаны друг с другом коэффициентом «близость» в диапазоне от 0 до 1, где коэффициент 1 означает, что два узла не имеют ничего общего, а 0 означает, что два узла абсолютно одинаковы.

Если два узла оба близки к другому узлу (т.е. они имеют коэффициент, близкий к 0), то это не означает, что они будут близко друг к другу, хотя вероятностно они имеют гораздо более высокий шанс быть близко друг к другу.

-

Вопрос:

Если в наборе находится другой узел, найдите узел, к которому он ближе всего, в кратчайшие сроки.

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

Я могу индексировать все узлы до того, как будет добавлен другой, и собирать данные о близости между каждым узлом, но если не сравнивать все узлы с новым узлом, я не смог найти эффективного решения. Любые идеи или помощь будут высоко ценится:)

Ответы [ 7 ]

1 голос
/ 15 апреля 2011

Поскольку ваша метрика «близость» подчиняется неравенству треугольника, вы должны иметь возможность использовать вариант BK-Trees для организации своих элементов.Адаптация их к действительным числам должна заключаться в выборе интервала для квантования вашего числа и в других случаях с использованием стандартной процедуры Bk-Tree.Некоторые эксперименты могут потребоваться - вы можете увеличить разрешение квантования, например, по мере продвижения вниз по дереву.

1 голос
/ 15 апреля 2011

В опросах ACM, проведенных в сентябре 2001 года, содержались две статьи, которые могли бы иметь отношение, по крайней мере, к исходным данным.«Поиск в метрических пространствах», ведущий автор Чавес, и «Поиск в многомерных пространствах - индексные структуры для повышения производительности мультимедийных баз данных», ведущий автор Бом.По памяти, если все, что у вас есть, это неравенство треугольника, вы можете использовать его для некоторого эффекта, но если вы можете урезать свои данные до разумного числа измерений, вы можете добиться большего успеха, используя структуру поиска, которая знает об этой структуре измерений.

1 голос
/ 15 апреля 2011

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

Например, если мы рассмотрим буквы - A близко к B, но далеко от Z - тогда уже существующие элементы можно отсортировать, скажем: A, B, E, G, K, M, Q, Z. Чтобы вставить, скажем, «F», вы начинаете со сравнения со средним элементом, [3] G, и следующим, что: [4] K. Вы устанавливаете, что F ближе к G, чем K, поэтому лучшее совпадение либо в G или налево, и мы двигаемся на полпути в неисследованную область слева ... 3/2 = [1] B, а затем E, и мы находим E ближе к F, поэтому совпадение либо в E, либо в это верно. Делим пополам пространство между нашими более ранними проверками в [3] и [1], мы проверяем в [2] и находим его одинаково удаленным, поэтому вставляем его между ними.

РЕДАКТИРОВАТЬ: он может работать лучше в вероятностных ситуациях и требовать меньшего количества сравнений, чтобы начинать с концов спектра и прокладывать себе дорогу (например, сравните F с A и Z, решите, что он ближе к A, посмотрите, ближе ли A или на полпути [3] G). Кроме того, было бы неплохо закончить сравнением с несколькими ближайшими точками по обе стороны от того места, куда вас привел двоичный код / ​​интерполяция.

1 голос
/ 15 апреля 2011

Если вам нужен оптимальный алгоритм с точки зрения скорости, но O (n ^ 2) места, то для каждого узла создайте отсортированный список других узлов (упорядоченных по близости).

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

Чтобы найти ближайший узел, просто найдите первый узел в любомсписок узлов.

Так как вам уже нужно пространство O (n ^ 2) (для хранения всей информации о близости вам нужна в основном матрица NxN, где A [i, j] представляет собой близость между i и j)Вы также можете отсортировать его и получить O (1).

1 голос
/ 15 апреля 2011

, но если не сравнивать все узлы с новым узлом, я не смог найти эффективного решения

Без какой-либо другой информации об отношениях между узлами этоединственный способ сделать это, так как вам нужно выяснить коэффициент близости между новым узлом и каждым существующим узлом.Алгоритм AO (n) может быть вполне приличным решением.

Единственное добавление, которое вы могли бы рассмотреть - имейте в виду, что мы не знаем, какую структуру данных вы используете для своих объектов, - это организовать все существующие узлы в граф.где узлы с коэффициентами ниже определенного порога можно считать связанными, поэтому вы можете сначала проверить узлы, которые с большей вероятностью будут похожи / связаны.

0 голосов
/ 15 апреля 2011

Это подозрительно похоже на задачу поиска ближайшего соседа (также называемую similarity search)

0 голосов
/ 15 апреля 2011

У Facebook есть такая вещь, где она помещает вас и всех ваших друзей в график, а затем медленно перемещает всех вокруг, пока люди не объединятся в группы на основе общих друзей и так далее.

Мне показалось, что они просто сделали что-то <0,5 привлекательной силой, что-нибудь> 0,5 силой отталкивания и перемещали людей с каждой итерацией, основываясь на чистой силе. После нескольких сотен итераций все выглядело чертовски хорошо.

Примечание: это не алгоритм, а эвристика. В реализации Facebook, которую я видел, два человека не смогли достичь равновесия и продолжали танцевать вокруг друг друга. Оказывается, они были на самом деле одним и тем же человеком с двумя разными аккаунтами.

Кроме того, на приличном компьютере это заняло около 15 минут и ~ 100 узлов. YMMV.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...