华子员工爆料:OD不丢人!大学室友去了华子正编,我半年后去了华子OD,天天在WeLink上和他侃大山!
正编固然是“金字塔顶端”,但也得为它付出超长的工作时间和心力。每次加班到深夜,心里就想着:这就算“正编”了?不过,咱也不能说不加班的“正编”就完全轻松,毕竟不少人也是“有理想才有加班”嘛,做的项目大多难度大、责任重,压力也随之增加。
OD的优势就是灵活,能让你有更多的时间去控制生活的节奏,活得比正编轻松得多。
算法题:非递减数列
问题是这样的:给定一个数组,要求判断它是否是一个非递减数列,即数组中的每个元素都不小于它前面的元素。如果是非递减的,返回true,否则返回false。
看一下例子:
输入: [1, 2, 2, 3],输出:true。输入: [1, 3, 2, 4],输出:false。
这个问题的核心就在于判断数组中的元素是否按非递减顺序排列。具体来说,如果数组中的任意两个相邻元素 nums[i] 和 nums[i + 1] 满足 nums[i] <= nums[i + 1],那么它就是一个非递减数列。
解决思路
这个问题其实可以通过一次遍历来解决。我们只需要从头到尾扫描整个数组,比较相邻的两个元素。如果发现有一个元素比它前面的元素小,那么直接返回false,否则继续检查。
简单实现:
public class NonDecreasingSequence {
public static boolean checkNonDecreasing(int[] nums) {
for (int i = 0; i < nums.length - 1; i++) {
if (nums[i] > nums[i + 1]) {
return false;
}
}
return true;
} public static void main(String[] args) {
int[] nums1 = {1, 2, 2, 3};
int[] nums2 = {1, 3, 2, 4};
System.out.println(checkNonDecreasing(nums1)); // 输出true
System.out.println(checkNonDecreasing(nums2)); // 输出false
}
}
代码讲解:
checkNonDecreasing方法接受一个整型数组nums,并逐一比较数组中的元素。我们通过一个 for循环遍历数组的每个元素,直到倒数第二个元素(因为我们要比较相邻的元素)。在每次迭代中,我们检查当前元素是否大于下一个元素。如果是,说明数组不是非递减数列,直接返回false。如果循环结束后都没有发现违背条件的情况,那就说明这个数组是非递减的,返回 true。
时间复杂度
这道题的时间复杂度是 O(n),其中 n 是数组的长度。因为我们只需要一次遍历整个数组,做常数时间的比较,所以效率是非常高的。
空间复杂度
空间复杂度是 O(1),因为我们只用了常数空间来存储一些临时变量,没有使用额外的空间来存储数据。
可能的优化
这道题其实没有太多可以优化的地方,因为最优解就是一次遍历,时间复杂度已经是最小了。即使采用了其他复杂的数据结构或算法,也无法做到比 O(n) 更好的时间复杂度。
小段子插入
说到“非递减”,不禁想到了日常生活中的一些例子。比如在工作中,有些人总是按部就班、稳扎稳打,从不冒进;而有些人,则是那种一开始就想要冲刺,结果没多久就摔得头破血流。看似前者一直保持一个“非递减”的节奏,实际上,也许走得慢点,但往往是稳妥的。哈哈,想想是不是有点共鸣?😄
其他思考
如果题目要求的是非递增数列,也就是要求数组中的每个元素不大于它前面的元素,我们只需要在比较时反过来判断即可:
if (nums[i] < nums[i + 1]) {
return false;
}
同样的算法,只是将条件取反,我们依然能够高效地解决这个问题。
总结
这道题虽然简单,但通过它可以帮助我们理清“排序”和“比较”的基本思路。通过一次遍历就能够高效地判断数组的顺序,避免了不必要的复杂操作,也可以在实际面试中展示自己的思维敏捷度和代码功底。对于一些简单的题目,不要心急,稳住,细节才是王道。
-END-
以上,就是今天的分享了,看完文章记得右下角给何老师点赞,也欢迎在评论区写下你的留言。