LeetCode刷题笔记:排序

题型一:多路快排
相关题目:75
解题思路:我们平时最常用的快速排序是二路快排,即将数组分为两部分然后分别递归排序。三路快排即将数组分为三部分,中间的部分是等于基准元素的部分,左边是小于基准元素的部分,右边是大于基准元素的部分。三路快排多用于数组中重复元素较多的情况。
例题:

//75
class SortColors {
    public void sortColors(int[] nums) {
    	quickSort3Ways(nums, 0, nums.length-1);
    }
    
    private void quickSort3Ways(int[] nums, int start, int end) {
    	if(start < end) {
    		int[] divide = partition(nums, start, end);
    		//递归start到中间区间的左边界-1部分
    		quickSort3Ways(nums, start, divide[0]-1);
    		//递归中间区间的右边界到end部分(注意这里右边界不用+1)
    		quickSort3Ways(nums, divide[1], end);
    	}
    }
    
    //partition函数的返回值是一个数组,因为要返回中间区间的左边界和右边界下标
    private int[] partition(int[] nums, int start, int end) {
    	//基准元素
    	int refer = nums[start];
    	//左边界
    	int left = start;
    	//右边界
    	int right = end+1;
    	//遍历数组的指针
    	int i = start+1;
    	//i<right而不是i<end是因为right右边的元素必定大于基准元素
    	while(i < right) {
    		//若i遍历到比基准元素小的元素,则交换i所在的元素和左边界+1的元素(+1是因为要始终让基准元素放在数组头)
    		//然后i后移,左边界后移
    		if(nums[i] < refer) {
    			swap(nums, i, left+1);
    			i++;
    			left++;
    		}
    		//若i遍历到比基准元素大的元素,则交换i所在的元素和右边界的元素
    		//这里注意i不用后移,因为交换过来的右边界所在元素仍需处理,前面交换过来的左边界所在元素必定比基准元素小所以不用处理
    		//右边界前移
    		else if(nums[i] > refer) {
    			swap(nums, i, right-1);
    			right--;
    		}
    		//若i遍历到与基准元素相等的元素,则i直接后移
    		else i++;
    	}
    	//将数组头的基准元素与中间区间的左边界元素交换
    	swap(nums, start, left);
    	//返回中间区间的左右边界下标
    	int[] divide = {left,right};
    	return divide;
    }
    
    private void swap(int[] nums, int a, int b) {
    	int temp = nums[a];
    	nums[a] = nums[b];
    	nums[b] = temp;
    }
}

每天一道LeetCode题,冲!!!

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

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

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值