问题描述
小U在一款挂机游戏中拥有n个英雄。游戏中有一种历练升级机制,每天可以选择两个英雄进行历练,如果两位英雄的等级相同,则他们的等级都不会改变。如果英雄等级不同,那么等级较高的英雄会增加1级,而等级较低的英雄则保持不变。
小U希望至少有一个英雄能够达到2000000000000000级,他想知道有多少英雄有潜力通过历练达到这个等级。
测试样例
样例1:
输入:
n = 5 ,u = [1, 2, 3, 1, 2]
输出:3
样例2:
输入:
n = 4 ,u = [100000, 100000, 100000, 100000]
输出:0
样例3:
输入:
n = 6 ,u = [1, 1, 1, 2, 2, 2]
输出:3
思路解析
题目分析
-
理解历练机制:
- 英雄等级不变:当两位英雄的等级相同时,经过历练后,两人的等级不会改变。
- 英雄等级提升:当两位英雄等级不同时,等级较高的英雄提升 1 级,而等级较低的英雄不变。
- 每天选择的两位英雄直接影响结果,因此通过历练,最终只有较高等级的英雄可以持续提升。
-
明确潜力英雄的条件:
- 若某个英雄的等级不等于最小等级(即
u[0]),则该英雄有机会通过历练增加自己的等级,因为可以选择与等级较低的英雄配对进行提升。 - 若某个英雄的等级等于最小等级,即使选择他进行历练,他的等级永远无法提升,因此他无法成为潜力英雄。
- 若某个英雄的等级不等于最小等级(即
-
转化问题:
- 题目最终转化为:计算出英雄等级高于最小等级的英雄数量。
解题思路
由上述分析可知,因为没有天数的限制,此题我们只需要获取大于最低等级的数有多少即可.
-
排序英雄等级:
- 通过排序,让所有英雄按照等级从低到高排列,便于快速找到最小等级(即
u[0])。
- 通过排序,让所有英雄按照等级从低到高排列,便于快速找到最小等级(即
-
遍历英雄等级:
- 从数组的尾部(等级最高)向前遍历,每遇到一个等级大于
u[0]的英雄,将其计入结果。
- 从数组的尾部(等级最高)向前遍历,每遇到一个等级大于
-
终止条件:
- 遍历到
u[0]时,说明后续英雄等级都等于最小等级,可以停止计数。
- 遍历到
-
计数结果:
- 返回所有等级大于
u[0]的英雄数量,即为有潜力达到目标等级的英雄数量。
- 返回所有等级大于
复杂度分析
-
时间复杂度:
- 排序:
O(n log n),这是代码中最耗时的操作。 - 遍历:
O(n),一次线性扫描计算等级大于最小值的英雄数量。 - 总体复杂度:
O(n log n)。
- 排序:
由于 java 语言原生对于排序的实现是 O(n^2) 的,因此使用 java 的时间复杂度会高于其他语言。
-
空间复杂度:
- 代码中只使用了常量级额外空间,因此空间复杂度为
O(1)。
- 代码中只使用了常量级额外空间,因此空间复杂度为
题解代码
public static int solution(int n, int[] u) {
Arrays.sort(u);
int count = 0;
for (int i = n - 1; i >= 0; i--) {
if(u[i] > u[0]) {
count++;
}
}
return count;
}