75.Sort Colors
给定一个数组,数组中包含元素0,1,2,要求在不使用sort库函数的情况下,实现数组排序。
Input: [2,0,2,1,1,0]
Output: [0,0,1,1,2,2]
思路:
一、因为只存在0,1,2这三个元素,所以可以用三个变量,分别记录数组中0,1,2出现的次数,最后再按照0,1,2的次数改写数组即可。相当于遍历2遍数组,第一遍记录次数,第二遍改写数组值。
class Solution { public: void sortColors(vector<int>& nums) { if (nums.empty()) return; int n0 = 0, n1 = 0, n2 = 0; for (int i = 0; i < nums.size(); i++) { if (nums[i] == 0) n0++; else if (nums[i] == 1) n1++; else n2++; } int idx = 0; while (n0--) nums[idx++] = 0; while (n1--) nums[idx++] = 1; while (n2--) nums[idx++] = 2; } };
二、要想只遍历一遍数组就将顺序排好。运用两根指针,一根指向头,一根指向尾,若遇到0,就跟left交换,left++,若遇到2,就跟right交换,right--,注意:防止遇到right的值也是2,则交换后当前下标对应的值还是2,所以,要判断交换后的值,而判断交换后的值,相当于将下标 i 重新移到当前位置再执行一轮,所以直接将当前下标 i-- ;遇到1,不处理。当left >= right 或者 i>right时,跳出循环。
class Solution { public: void sortColors(vector<int>& nums) { if (nums.empty()) return; int n = nums.size(), left = 0, right = n - 1; for (int i = 0; i < n; i++) { if (left >= right || i > right) break; if (nums[i] == 0) { swap(nums[left], nums[i]); left++; } else if(nums[i]==2) { swap(nums[i], nums[right]); right--; i--;// i 的下标减一位 } } } };