简体   繁体   English

如何计算网格上两个方块之间的距离,包括目标方块

[英]How do I calculate the distance between two squares on a grid, including the target square

I've been trying variations on the following code...我一直在尝试对以下代码进行变体...

public int Distance2D(int x1, int y1, int x2, int y2)
{
    //     ______________________
    //d = √ (x2-x1)^2 + (y2-y1)^2
    //

    //Our end result
    int result = 0;
    //Take x2-x1, then square it
    double part1 = Math.Pow((x2 - x1), 2);
    //Take y2-y1, then sqaure it
    double part2 = Math.Pow((y2 - y1), 2);
    //Add both of the parts together
    double underRadical = part1 + part2;
    //Get the square root of the parts
    result = (int)Math.Sqrt(underRadical);
    //Return our result
    return result;
}

The examples below are left for clarity, but were wrong due to my mistake下面的例子是为了清楚起见,但由于我的错误而错误

Distance2D(1, 1, 1, 2) // returns 1 - correct Distance2D(1, 1, 1, 2) // 返回 1 - 正确
Distance2D(1, 1, 2, 1) // returns 1 - correct Distance2D(1, 1, 2, 1) // 返回 1 - 正确
Distance2D(1, 1, 2, 2) // returns 1 - correct Distance2D(1, 1, 2, 2) // 返回 1 - 正确
Distance2D(1, 1, 5, 5) // returns 5 - correct Distance2D(1, 1, 5, 5) // 返回 5 - 正确

Distance2D(0, 2, 5, 8) // returns 7 - incorrect, should be 8 Distance2D(0, 2, 5, 8) // 返回 7 - 不正确,应该是 8
Distance2D(1, 1, 5, 3) // returns 4 - incorrect, should be 5 Distance2D(1, 1, 5, 3) // 返回 4 - 不正确,应该是 5
Distance2D(10, 112, 15, 118) // returns 7 - incorrect, should be 8 Distance2D(10, 112, 15, 118) // 返回 7 - 不正确,应该是 8

Is there a better formula for this?有没有更好的公式?

Update更新

I had some of my expected values above incorrect due to mistakenly taking the origin of the 2nd coordinate from the location of the 1st.由于错误地从第一个坐标的位置取第二个坐标的原点,我的一些预期值不正确。

I'm trying to get the number of moves a game piece would need to make to travel from one coordinate to another on a square grid.我试图获得一个游戏块在方形网格上从一个坐标移动到另一个坐标所需的移动次数。 Moving one square at a time, diagonals count as 1 move also.一次移动一格,对角线也算作 1 次移动。

Thus ...因此 ...

  • from 1,1 to 5,5 would take 4 diagonal movements and one horizontal/vertical move for a total of 5 moves.从 1,1 到 5,5 需要 4 次对角线移动和 1 次水平/垂直移动,总共 5 次移动。 This returns correctly这正确返回
  • from 1,1 to 5,3 would take 3 diagonal and 1 horizontal/vertical move for a total of 4 moves.从 1,1 到 5,3 需要 3 次对角线和 1 次水平/垂直移动,总共 4 次移动。 This now returns correctly这现在正确返回
  • from 1,1 to any of 1,2/2,1/2,2 is one move.从 1,1 到 1,2/2,1/2,2 中的任何一个都是一个移动。 These each return correctly这些都正确返回
  • from 0,2 to 5,8 is 5 diagonal moves and one vertical move for a total of 6 moves.从 0,2 到 5,8 是 5 次对角线移动和 1 次垂直移动,总共 6 次移动。 This returns 7 incorrectly这会错误地返回 7

If I use Math.Round() on the result then I get the following errors...如果我在结果上使用Math.Round()那么我会得到以下错误......

  • from 0,2 to 5,8 returns 8 instead of 6从 0,2 到 5,8 返回 8 而不是 6
  • 1,1 to 5,5 returns 6 instead of 5 1,1 到 5,5 返回 6 而不是 5

If I use Math.Ceiling() I get the following errors...如果我使用Math.Ceiling()我会收到以下错误...

  • 0,2 to 5,8 returns 8 instead of 6 0,2 到 5,8 返回 8 而不是 6
  • 1,1 to 2,2 returns 2 instead of 1 1,1 到 2,2 返回 2 而不是 1
  • 1,1 to 5,3 returns 4 instead of 5 1,1 到 5,3 返回 4 而不是 5

The problem is that performing a cast ( (int) ) effectively does a "floor" operation on your number, cutting off any decimal values, even if those decimal values are .99999 .问题是执行.99999 ( (int) ) 有效地对您的数字执行“地板”操作,切断任何十进制值,即使这些十进制值是.99999 It sounds like you're looking instead to round the value to the nearest integer, which can be done with the Math.Round() function.听起来您希望将值四舍五入到最接近的整数,这可以使用Math.Round()函数来完成。

Try this:尝试这个:

result = (int)Math.Round(Math.Sqrt(underRadical));

Update更新

The pythagorean theorem-based approach you're taking won't work for what you're trying to calculate.您采用的基于勾股定理的方法不适用于您要计算的内容。 This is a completely different use case.这是一个完全不同的用例。 Good news is, your use case is a lot simpler.好消息是,您的用例要简单得多。 Just figure out the distance you'd have to travel on each axis, then subtract whatever shortcuts you can take by moving diagonally.只需计算出您必须在每个轴上行驶的距离,然后减去您可以通过对角移动来走的任何捷径。 Something like this, I think:像这样的事情,我认为:

var yDist = Math.Abs(y2 - y1);
var xDist = Math.Abs(x2 - x1);
var diagShortcut = Math.Min(yDist, xDist);
return yDist + xDist - diagShortcut;

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM