给一个 \(n \times n\) 的矩阵, \(n\) 是偶数。将矩阵按圈分割,同一圈的位置可以不消耗代价移动,可以消耗一个代价移动到相邻圈。
给出 \(n, x_1, y_1, x_2, y_2\) ,询问 \((x_1, y_1)\) 移动到 \((x_2, y_2)\) 的代价最小是多少。
显然对每个圈可以选择左上角作为定点。
- 显然直线 \(f(i) = n - j\) 左侧的点 \((a, b)\) 可以直接定位到定点 \(min(a, b)\) 。这些点满足 \(a + b \leq 1 + n\) 。
- 直线 \(f(i) = n - j\) 右侧的点 \((a, b)\) 经过 \((\frac{n}{2},\frac{n}{2})\) 中心对称后还在同一圈,且可以移到左侧。
假设 \((x_1', y_1'), (x_2', y_2')\) 都是调整过的点,则答案为 \(|min(x_1', y_1') - min(x_1', y_1')|\) 。
view
#include <bits/stdc++.h>
typedef long long ll;
void solve(){
int n, x_1, y_1, x_2, y_2; std::cin >> n >> x_1 >> y_1 >> x_2 >> y_2;
if (x_1 + y_1 > n + 1) x_1 = n + 1 - x_1, y_1 = n + 1 - y_1;
if (x_2 + y_2 > n + 1) x_2 = n + 1 - x_2, y_2 = n + 1 - y_2;
std::cout << abs(std::min(x_1, y_1) - std::min(x_2, y_2)) << '\n';
}
int main() {
int _ = 1; std::cin >> _;
while (_--) solve();
return 0;
}