Как лучше всего сравнить координаты двух узлов?

У меня есть график, и каждый узел имеет свое местоположение в виде пары (x, y), Я хочу сравнить евклидово расстояние двух узлов и назначить новое свойство или тег в соответствии с их расстоянием.

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

Например: если есть node1 (1, 1) а также node2(1, 2)они почти соседи и имеют сильное сходство. Но node3(51, 48) далеко от node1 а также node2,

Один из способов — проверить каждый интервал расстояния между двумя узлами:

if(dist == a)
map<pair<node, node>, taga>
if(dist == b)
map<pair<node, node>, tagb>
if(dist == c)
map<pair<node, node>, tagc>
.
.
.
if(dist == z)
map<pair<node, node>, tagz>

Каков наилучший способ поставить эти интервалы? Я думаю, что приведенный выше алгоритм требует много условий, если график большой и распределен по площади.

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

Есть ли эффективный подход?

2

Решение

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

Сначала проверьте эту функцию:

int get_distance(std::pair<int, int> const pos_a, std::pair<int, int> const pos_b)
{
auto const distance_x = pos_a.first >= pos_b.first ? pos_a.first - pos_b.first : pos_b.first - pos_a.first;
auto const distance_y = pos_a.second >= pos_b.second ? pos_a.second - pos_b.second : pos_b.second - pos_a.second;
if (distance_x != 0 && distance_y != 0)
return int(round(sqrt(distance_x * distance_x + distance_y * distance_y)));
if (distance_x == 0)
return distance_y;
return distance_x;
}

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

Третья строка — это оператор if, оценивающий, являются ли оба полученных расстояния ненулевая потому что если они есть, то они находятся на одной линии по вертикали или по горизонтали …

Если оба являются ненулевая числа, затем сумма квадратного корня из квадратов расстояния x и y округляется до ближайшего целого числа, а затем приводится к целому числу (так как тип возвращаемого значения ИНТ)

С другой стороны, если любой из них является нуль число (следовательно, на одной линии), то расстояние Икс или же Y будет возвращено соответственно на основе оси линии (вертикальной или горизонтальной, следовательно, distance_x == 0 а также distance_y == 0)

Теперь для вашей другой проблемы, а именно Близость, о которой упоминалось выше, можно объявить перечислителем, который хранит значение для такого рода вещей …

Пример:

enum Distance
{
DISTANCE_VERY_CLOSE = 1,
DISTANCE_CLOSE,
DISTANCE_RELATIVELY_CLOSE,
DISTANCE_RELATIVELY_FAR,
DISTANCE_FAR,
DISTANCE_VERY_FAR,
DISTANCE_EXTREMELY_FAR
};

Затем этот перечислитель будет отслеживать расстояние для вас, так что вам просто нужно использовать этот макрос для преобразования целого числа в Distance (Перечислитель) …

#define TO_DISTANCE(distance) ((distance) > 7 ? Distance(7) : Distance(distance))

Это простой макрос, который просто приводит целое число к счетчику и приводит цифру 7, если расстояние больше 7 (следовательно, DISTANCE_EXTREMELY_FAR). Однако вы можете пойти дальше и добавить больше в перечислитель, если хотите. (Только не забудьте изменить значение 7 на последнее enum член имеет)

Пример использования вышеуказанного метода:

int main()
{
auto const dist = TO_DISTANCE(get_distance(std::make_pair(20, 20), std::make_pair(30, 30)));
accuracy *= dist; // Multiplying accuracy to distance (Hence, increases)
// Note: The accuracy needs to be at least 1 or more for this to work...
// You can check the "closeness" like this...
if (dist == DISTANCE_FAR)
std::cout << "They are far away from each other" << std::endl;
// Some other code goes here ...
return 0;
}

С уважением,

Ruks.

0

Другие решения

Других решений пока нет …

По вопросам рекламы ammmcru@yandex.ru
Adblock
detector