比较两个节点坐标的最佳方法是什么?
What is the best way compare two nodes coordinates?
我有一个图,每个节点的位置都是一对 (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>
放置此间隔的最佳方式是什么?我认为上述算法需要很多条件,如果图形很大并且分布在区域周围。
标签可以是节点或连接到它们的边的权重,因此邻近节点可以具有相似的权重。
有没有有效的方法?
如果我对你的问题理解正确,你想检查两个点(位置)之间的接近度,这两个点(位置)可能相距很远,也可能相距不远。
先看看这个函数:
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;
}
在这里,它通过用最大数减去两点来计算两点之间的距离(因此是两个开头的语句),使用的运算符是 Ternary Operator。 (如果你不知道那是什么,请点击link)
第三行是一个 if 语句,判断两个获取的距离是否非零,因为如果是,那么它们在垂直或水平方向上在同一条线上...
如果都是 非零数,则距离x和y的平方根和平方根四舍五入为最近的整数,然后将自身转换为整数(因为 return 类型是 int)
另一方面,如果其中任何一个是一个零数字(因此,在同一行),那么距离 X 或 Y 将根据线轴(垂直或水平,因此 distance_x == 0
分别 returned ] 和 distance_y == 0
)
现在,对于你的另一个问题,viz. Closeness,上面提到过,一种方法是声明一个枚举器来存储这种东西的值......
Example:
enum Distance
{
DISTANCE_VERY_CLOSE = 1,
DISTANCE_CLOSE,
DISTANCE_RELATIVELY_CLOSE,
DISTANCE_RELATIVELY_FAR,
DISTANCE_FAR,
DISTANCE_VERY_FAR,
DISTANCE_EXTREMELY_FAR
};
Then this enumerator will keep track of the distance for you, so you just need to use this macro to convert an integer to Distance
(The enumerator)...
#define TO_DISTANCE(distance) ((distance) > 7 ? Distance(7) : Distance(distance))
This is a simple macro that just simply casts an integer to the enumerator and casts the digit 7 if the distance is more than 7 (Hence, DISTANCE_EXTREMELY_FAR
). However, you can go ahead and add more inside the enumerator if you want. (Just remember to change 7 to the value the last enum
member has)
上述方法的使用示例:
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;
}
亲切的问候,
卢克。
我有一个图,每个节点的位置都是一对 (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>
放置此间隔的最佳方式是什么?我认为上述算法需要很多条件,如果图形很大并且分布在区域周围。
标签可以是节点或连接到它们的边的权重,因此邻近节点可以具有相似的权重。
有没有有效的方法?
如果我对你的问题理解正确,你想检查两个点(位置)之间的接近度,这两个点(位置)可能相距很远,也可能相距不远。
先看看这个函数:
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;
}
在这里,它通过用最大数减去两点来计算两点之间的距离(因此是两个开头的语句),使用的运算符是 Ternary Operator。 (如果你不知道那是什么,请点击link)
第三行是一个 if 语句,判断两个获取的距离是否非零,因为如果是,那么它们在垂直或水平方向上在同一条线上...
如果都是 非零数,则距离x和y的平方根和平方根四舍五入为最近的整数,然后将自身转换为整数(因为 return 类型是 int)
另一方面,如果其中任何一个是一个零数字(因此,在同一行),那么距离 X 或 Y 将根据线轴(垂直或水平,因此 distance_x == 0
分别 returned ] 和 distance_y == 0
)
现在,对于你的另一个问题,viz. Closeness,上面提到过,一种方法是声明一个枚举器来存储这种东西的值......
Example:
enum Distance { DISTANCE_VERY_CLOSE = 1, DISTANCE_CLOSE, DISTANCE_RELATIVELY_CLOSE, DISTANCE_RELATIVELY_FAR, DISTANCE_FAR, DISTANCE_VERY_FAR, DISTANCE_EXTREMELY_FAR };
Then this enumerator will keep track of the distance for you, so you just need to use this macro to convert an integer to
Distance
(The enumerator)...
#define TO_DISTANCE(distance) ((distance) > 7 ? Distance(7) : Distance(distance))
This is a simple macro that just simply casts an integer to the enumerator and casts the digit 7 if the distance is more than 7 (Hence,
DISTANCE_EXTREMELY_FAR
). However, you can go ahead and add more inside the enumerator if you want. (Just remember to change 7 to the value the lastenum
member has)
上述方法的使用示例:
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;
}
亲切的问候,
卢克。