题目
给定一个包含红色、白色和蓝色、共 n 个元素的数组 nums ,原地对它们进行排序,使得相同颜色的元素相邻,并按照红色、白色、蓝色顺序排列。
我们使用整数 0、 1 和 2 分别表示红色、白色和蓝色。
必须在不使用库内置的 sort 函数的情况下解决这个问题。
示例 1:
输入:nums = [2,0,2,1,1,0]
输出:[0,0,1,1,2,2]
示例 2:
输入:nums = [2,0,1]
输出:[0,1,2]
提示:
n == nums.length
1 <= n <= 300
nums[i] 为 0、1 或 2
本人解题
因为题目中可以得知,大部分的数组元素都是相等的,所以使用希尔排序是最快的。
class Solution {
public:
void sortColors(vector<int>& nums) {
int n = nums.size();
int d = n/2;
while(d>0){
for(int i = 0;i<n;i+=d){
int index = nums[i];
for(int j = i;j>0 && index < nums[j-d];j-=d){
swap(nums[j],nums[j-d]);
}
}
d=d/2;
}
}
};
重新练习一下堆排序也是可以的。。。
class Solution {
public:
void sortColors(vector<int>& nums) {
unordered_map<int,int> map;
for(int n : nums){
map[n]++;
}
nums.clear();
for(int i = 0;i<3;i++){
int cnt = map[i];
for(int j = 0;j<cnt;j++){
nums.push_back(i);
}
}
}
//建立大顶堆
void buildHeap(vector<int> &nums,int begin,int end){
int parent = begin;
int child = 2 * parent + 1;
while(child<end){
if(child < end - 1 && nums[child] < nums[child++]){
child++;
}
if(nums[parent]>=nums[child]){
return;
}
swap(nums[parent],nums[child]);
parent = child;
child = 2 * parent + 1;
}
}
//堆排序
void sortHeap(vector<int> & nums){
int n = nums.size();
for(int i = n / 2 - 1;i>0;i--){
buildHeap(nums,i,n-1);
}
for(int i = n;i>0;i--){
buildHeap(nums,0,i);
swap(nums[0],nums[i]);
}
}
};
或者直接使用一个map的结构记录三种元素的个数,再重新插入数组也是可行的
class Solution {
public:
void sortColors(vector<int>& nums) {
unordered_map<int,int> map;
for(int n : nums){
map[n]++;
}
nums.clear();
for(int i = 0;i<3;i++){
int cnt = map[i];
for(int j = 0;j<cnt;j++){
nums.push_back(i);
}
}
}
};