Четырехъядерные деревья
Четырехъядерное дерево занимает квадрат пространства и делит его на четыре дочерних элемента с половиной размеров по осям X и Y.
+---+---+
| | | Each square is a child
| | | of the parent; when you
+---+---+ get to leaves a node has
| | | a single point or a list
| | | of points.
+---+---+
Эта структура данных является рекурсивной, и вы ищете точки, проверяя, какой из них удерживает точку, пока не дойдете до листа.Лист имеет один элемент (точка с координатами X, Y) или список членов, в зависимости от реализации.Если вы заполняете узел, вы разделяете его на 4 и распределяете дочерние элементы.По сути, структура данных является обобщением двоичного дерева, поэтому оно не обязательно сбалансировано.
Балансирование четырехугольного дерева может быть необязательным для ваших целей и оставлено в качестве упражнения для читателя - попробуйте поискать в Интернете «сбалансированное четырехугольное дерево»
Обратите внимание, что эта структура данных не можетиндексировать элементы, которые могут перекрываться, но если вы сохраняете только точки, это не будет проблемой.
Поиск ближайших соседей в четырехугольном дереве
С вершинымоей головы, вот быстрый и грязный алгоритм для поиска 'n' ближайших соседей к вашей точке.Это не обязательно эффективно с точки зрения оптимизации, но это будет довольно просто реализовать.Если у кого-то есть ссылка на лучшую ссылку, отправьте ее в комментарии или ответе.
Найдите узел дерева четырехугольников, содержащий вашу точку, и сохраните список его родителей.
Поместите все точки в узле в приоритетную очередь на основе их расстояния от вашей базовой точки (т.е. по длине гипотенузы согласно теореме Пифагора).В зависимости от реализации может быть один или несколько на узел.Для простой реализации структуры данных очереди с приоритетами ищите «двоичную кучу».
Если какая-либо из точек 'n' находится дальше, чем края ограничительной рамки, добавьтесодержимое своих соседей.т.е. если ваша базовая точка находится близко к краю ограничивающей рамки, возможно, что соседние узлы дерева могут содержать точки, которые находятся ближе, чем точки, найденные в пределах вашей ограничительной рамки.Для этого вам необходимо создать резервную копию дерева, поэтому вам необходимо отслеживать родительские узлы.
Когда все n ближайших точек находятся ближе, чемКрая вашей ограничительной рамки, вы знаете, что не может быть соседей, которых вы пропустили.Следовательно, 'n' ближайшие точки в этом поле должны быть вашими 'n' ближайшими соседями.