国际象棋跳跃问题C++题解 | 豆包MarsCode AI刷题

103 阅读2分钟

问题描述

小U掌握了国际象棋中“象”和“马”的跳跃能力,在一个无限大的平面直角坐标系中,她每一步可以模仿象和马的跳跃方式移动。在每次询问中,小U需要计算从初始坐标 (x1,y1)(x_1, y_1)(x2,y2)(x_2, y_2) 所需的最少步数。

  • 象的跳跃:可以移动到 (x+k,y+k)(x + k, y + k)(x+k,yk)(x + k, y - k),其中 kk 是任意整数。
  • 马的跳跃:可以移动到 (x+a,y+b)(x + a, y + b),其中 a+b=3|a| + |b| = 31a,b21 \leq |a|, |b| \leq 2

你需要在每次询问中计算从起点到终点所需的最少步数。

测试样例

样例1:

输入:x1 = 0, y1 = 0, x2 = 1, y2 = 1 输出:1

样例2:

输入:x1 = 0, y1 = 0, x2 = 2, y2 = 1 输出:1

样例3:

输入:x1 = 0, y1 = 0, x2 = 3, y2 = 3 输出:1

样例4:

输入:x1 = -3, y1 = -2, x2 = 2, y2 = 1 输出:2

解题思路

因为k大小没有限制,要保证最小步数应优先使用"象"进行移动。

初、末位置为矩形对角线或直线

设初位置为A,末位置为B;

新建位图图像.bmp

d1、d2分别为俩正方形的边长;

由图可知"d1+d2=L","d1-d2=H",解得2d1=L+H;

分类讨论

情况一:若初始位置与最终位置连线恰为正方形对角线,则步数为1;

情况二:若L+H为偶数则d1有解,移动方式为两次"象",步数为2;

情况三:若L+H=3则可通过“马”一次到达,步数为1;

若L+H为奇数,我们可以以“马”的方式移动一次,“L变化2,H变化1”,或“L变化1,H变化2”,变化2不影响奇偶性,变化1改变奇偶性,所以L+H变为偶数;

情况四:若此时L=H则步数为2,“马”+“象”

情况五:若不等则步数为3,“马”+“象1”+“象2”

A,B成直线时结论仍然成立。

#include <iostream>
int solution(int x1, int y1, int x2, int y2) {
  int dx = abs(x1 - x2), dy = abs(y1 - y2);//计算两点x,y轴距离
  if (dx == dy) {   //情况一
    if (dx == 0)
      return 0;
    return 1;
  }
  if ((dx + dy) % 2 == 0)   //情况二
    return 2;
  if (dx < dy)       //保证dx为矩形的长,dy为宽
    std::swap(dx, dy); 
  if (dx + dy == 3)  //情况三
     return 1;
  if (dx - dy == 1 || dx - dy == 3) {  //情况四,成矩形时,长宽相差为1或3,可通过“马”移动变为正方形
    return 2;
  }    
   return 3;   //情况五
}

int main() {
  std::cout << (solution(0, 0, 1, 1) == 1) << std::endl;
  std::cout << (solution(0, 0, 2, 1) == 1) << std::endl;
  std::cout << (solution(0, 0, 3, 3) == 1) << std::endl;
  std::cout << (solution(-3, -2, 2, 1) == 2) << std::endl;
}