一、需求
给定一个数组 nums,编写一个函数将所有 0 移动到数组的末尾,同时保持非零元素的相对顺序。
示例:
- 输入: [0,1,0,3,12]
- 输出: [1,3,12,0,0]
说明:
- 必须在原数组上操作,不能拷贝额外的数组。
- 尽量减少操作次数。
二、题解一
class Solution {
public void moveZeroes(int[] nums) {
int index = 0;
for (int i = 0, length = nums.length; i < length; i ++) {
if (nums[i] != 0) {
nums[index ++] = nums[i];
}
}
while (index < nums.length) {
nums[index ++] = 0;
}
}
}
三、思路一
1.首先定义一个index来标记数组元素的位置地址
2.遍历原数组,判断每一个元素是否为0
3.若不为0,则将其放到原数组的index位置中,且index++
4.再次遍历原数组,条件是index小于数组长度(代表原数组中存在为0的元素,元素为0的个数为数组长度-index),所以有while (index < nums.length) {index ++}
5.将0补充到数组末尾即可,nums[index ++] = 0;
四、结果一
附上LeetCode的结果。这里时间复杂度为O(n)。
五、题解二
class Solution {
public void moveZeroes(int[] nums) {
int index = 0;
for (int i = 0, length = nums.length; i < length; i ++) {
if (nums[i] != 0) {
nums[index] = nums[i];
if (i != index) {
nums[i] = 0;
}
index ++;
}
}
}
}
六、思路二
和思路一类似,但是比思路一少了一层循环,效率更佳。
直接代数法求证:
假设数组[0,1,0,3,12]
第一轮循环:[0,1,0,3,12],i=0
第二轮循环:[1,0,0,3,12],i=1
第三轮循环:[1,0,0,3,12],i=2
第四轮循环:[1,3,0,0,12],i=3
第五轮循环:[1,3,12,0,0],i=4
七、结果二
附上LeetCode的结果。这里时间复杂度为O(n)。明显比方案一少了一层循环,效率更佳。