一、Problems
Given an array nums
, write a function to move all 0
's to the end of it while maintaining the relative order of the non-zero elements.
Example:
Input:[0,1,0,3,12]
Output:[1,3,12,0,0]
Note:
- You must do this in-place without making a copy of the array.
- Minimize the total number of operations.
二、Solution
给定一个数组nums,写一个函数,将数组所有0挪到数组末尾,而维持其他所有非0元素相对位置。
思路1:遍历一遍数组将非0元素拿出来放入辅助数组中,再将拿出来的非0元素放回到原数组中,将原数组没添补的位置赋值为0.
需求:1)需将非0元素拿出来:先声明个辅助数组。
2)遍历一遍数组:需一个for循环。
3)判断是否非0:需一个if语句。
4)将非0元元素再次放回原数组中:又需一次for循环。
5)将没添补的位置赋值为0:需明确索引范围再次for循环。
c++ 代码:
class Solution { public: vector<int> nonZero; // 声明一个辅助数组用于存放非0元素 void moveZeroes(vector<int>& nums) { for (int i = 0; i < nums.size(); i++) // 扫描一遍原数组 if (nums[i]) // 如果 是非0元素 nonZero.push_back(nums[i]); // pushback 进 辅助数组中 for (int i = 0; i < nonZero.size(); i++) // 遍历辅助数组 nums[i] = nonZero[i]; //将其中非0元素放回到原数组中 for (int i = nonZero.size(); i < nums.size(); i++) // 0元素索引开始位置在辅助数组大小处 但要小于原数组大小 nums[i] = 0; // 将这段区间的元素 赋值为0 } };
时间复杂度O(n)
空间复杂度 O(n) 因为开辟了额外的辅助空间,即不是一个原地的算法。
思路2:
不用辅助空间,原地遍历数组将非0元素放到数组前面,设置索引k,[0 k)区间中保存所有当前遍历过的非0元素。
c++代码:
// 非0原地移动 不需额外空间 空间复杂度为O(1) class Solution { public: void moveZeroes(vector<int>& nums) { int k = 0; // 设置一个索引k 初值为0 即指向原数组索引为0的位置 // 程序遍历完后 [0 k)区间为非0元素 for (int i = 0; i < nums.size(); i++) //索引i 从数组初始位置开始遍历 if (nums[i]) // 如果索引i当前遍历的元素非0 nums[k++] = nums[i]; //则将i指向的当前元素 赋值给k当前所指位置,然后k索引后移一位 for (int i = k; i < nums.size(); i++) // 将原数组剩余位置赋值为0 范围[k nums.size) nums[i] = 0; } };
代码参考:https://github.com/liuyubobobo/Play-Leetcode