快速排序模板

手写快排模板

void quick_sort(int q[], int l, int r)
{
    if (l >= r) return;
	
    int i = l-1, j = r+1, x = q[(l+r)>>1];//先移动,再判断。因此i, j的初始位置分别位于l, r的两侧。
    while(i < j) {
        while (q[++i] < x);//不取等号,(若x为最大值,则i会一直++)防止数组越界
        while (q[--j] > x);//先移动,再判断。防止不移动,在外面卡住
        if (i < j) swap(q[i], q[j]);
    }

    quick_sort(q, l, j);//这里j有没有可能为r?(中枢是向下取整,故不可能)
    quick_sort(q, j + 1, r);//这里j+1有没有可能为l?
}

模板中有以下几点需要注意:

  1. 分治算法最怕把n分成0和n,因为这样可能造成无限划分。
  2. while (q[++i] < x);中的条件不能带等号,如果带等号可能造成下标增加到r + 1,导致数组越界。
  3. if (i < j) 条件中可以加上等号,因为i == j时表示自己和自己交换,因此没有任何影响。
  4. 这里一定要选择j作为枢轴元素。并且左边部分递归区间是[l, j],右边部分递归区间是[j + 1, r]。如果选择i作为枢轴元素的话算法是有问题的。因为最终q[i] >= x,并不一定在左边部分区间。当然也可以稍作改动使得可以使用i - 1作为分界点。
  5. 注意这里是先移动,再判断。因此i, j的初始位置分别位于l, r的两侧。因为两个指针在每次交换完之后都需要向中间移动一位,因此我们可以每次上来就先移动一次,这样我们就需要把指针的初始值放到外侧。

使用 i 作为分界点的快排模板

void quick_sort(int q[], int l, int r)
{
    if (l >= r) return;

    int i = l - 1, j = r + 1, x = q[l + r + 1 >> 1];
    while (i < j)
    {
        do i++; while (q[i] < x);
        do j--; while (q[j] > x);
        if (i < j) swap(q[i], q[j]);
    }

    quick_sort(q, l, i - 1);
    quick_sort(q, i, r);
}

LC347. 前 K 个高频元素

给你一个整数数组 nums 和一个整数 k ,请你返回其中出现频率前 k 高的元素。你可以按 任意顺序 返回答案。

class Solution {
public:
    vector<pair<int, int>> vec;
    vector<int> ans;

    void myqsort(int l, int r, int k) {
        if(l >= r) {
            if(l == k-1 && r == k-1) {
                ans.push_back(vec[l].first);
            }
            return;
        }

        int i = l-1, j = r+1, mid = vec[(l+r)>>1].second;
        while(i < j) {
            while(vec[++i].second > mid);
            while(vec[--j].second < mid);
            if(i < j)   swap(vec[i], vec[j]);
        }
        
        if(j <= k-1) {
            for(int x = l; x <= j; ++x) {
                ans.push_back(vec[x].first);
            }
            if(j < k-1)   myqsort(j+1, r, k);
        } else {
            myqsort(l, j, k);
        }
    }
    vector<int> topKFrequent(vector<int>& nums, int k) {
        unordered_map<int, int> ump;

        for(int a : nums)   ump[a]++;
        for(auto iter : ump)    vec.push_back(iter);
        //for(auto v : vec)   cout << v.first << "-->" << v.second << endl;

        myqsort(0, vec.size()-1, k);

        return ans;
    }
};
  • 0
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值