问题描述
小S正在玩一个关于石子的游戏,给定了一些石子,它们位于一维数轴的不同位置,位置用数组 stones 表示。如果某个石子处于最小或最大的一个位置,我们称其为端点石子。
在每个回合,小S可以将一颗端点石子移动到一个未占用的位置,使其不再是端点石子。游戏继续,直到石子的位置变得连续,无法再进行任何移动操作。
你需要帮助小S找到可以移动的最大次数。
使用算法
贪心 + 排序
算法思路
-
排序:
- 首先,将数组
stones进行排序,以便于分析石子的位置。
- 首先,将数组
-
处理特殊情况:
- 如果石子的数量小于等于2,那么它们已经是连续的,无法进行任何移动操作,直接返回0。
-
计算最小空隙:
- 计算最小的端点石子移动次数,即
min,它是第一个石子和第二个石子之间空隙的大小,以及最后一个石子和倒数第二个石子之间空隙的大小中的较小值。
- 计算最小的端点石子移动次数,即
-
计算总空隙:
- 遍历排序后的石子数组,计算所有相邻石子之间的空隙总和,即
diff。
- 遍历排序后的石子数组,计算所有相邻石子之间的空隙总和,即
-
计算最大移动次数:
- 最大移动次数是总空隙
diff减去最小空隙min。
- 最大移动次数是总空隙
-
返回结果:
solution函数返回最大移动次数。
代码展示
import java.util.Arrays;
public class Main {
public static int solution(int[] stones) {
// write code here
Arrays.sort(stones);
if (stones.length <= 2) {
return 0;
}
//
int min = Math.min(stones[1] - stones[0] - 1, stones[stones.length - 1] -
stones[stones.length - 2]-1);
int diff = 0;
int pre = -1;
for (int i = 0; i < stones.length; i++) {
if (i == 0) {
pre = stones[0];
} else {
diff += stones[i] - pre - 1;
pre = stones[i];
}
}
return diff - min;
}
public static void main(String[] args) {
System.out.println(solution(new int[] { 7, 4, 9 }) == 2);
System.out.println(solution(new int[] { 6, 5, 4, 3, 10 }) == 3);
System.out.println(solution(new int[] { 1, 2, 3, 4, 5 }) == 0);
}
}