1033. 移动石子直到连续
三枚石子放置在数轴上,位置分别为 a
,b
,c
。
每一回合,你可以从两端之一拿起一枚石子(位置最大或最小),并将其放入两端之间的任一空闲位置。形式上,假设这三枚石子当前分别位于位置 x, y, z
且 x < y < z
。那么就可以从位置 x
或者是位置 z
拿起一枚石子,并将该石子移动到某一整数位置 k
处,其中 x < k < z
且 k != y
。
当你无法进行任何移动时,即,这些石子的位置连续时,游戏结束。
要使游戏结束,你可以执行的最小和最大移动次数分别是多少? 以长度为 2 的数组形式返回答案:answer = [minimum_moves, maximum_moves]
示例 1:
输入:a = 1, b = 2, c = 5
输出:[1, 2]
解释:将石子从 5 移动到 4 再移动到 3,或者我们可以直接将石子移动到 3。
题解
我们先将 a,b,c 排序,记为 x,y,z, 即 x<y<z。
接下来分情况讨论:
如果 z−x≤2,说明 3 个数已经相邻,不用移动,结果为 [0,0];
否则,如果 y−x<3,或者 z−y<3,说明有两个数只间隔一个位置,我们只需要把另一个数移动到这两个数的中间,最小移动次数为 1;其他情况,最小移动次数为 2;
最大移动次数就是两边的数字逐个往中间靠,最多移动 z−x−2 次。
最后将最小移动次数、最大移动次数返回即可。
class Solution {
public:
vector numMovesStones(int a, int b, int c) {
int x = min({a, b, c});
int z = max({a, b, c});
int y = a + b + c - x - z;
int mi = 0, mx = 0;
if (z - x > 2) {
mi = y - x < 3 || z - y < 3 ? 1 : 2;
mx = z - x - 2;
}
return {mi, mx};
}
};