快速排序(递归实现)

在这里插入图片描述 在这里插入图片描述在这里插入图片描述
1.哨兵位置为最终位置
2.partition就是切分过程
3.选择一个哨兵,将一组数划分为全比它小、全比它大的左右两部分,再分别对这两部分继续如此左右划分,直到元素个数为1.整个划分结束时,数组已排好序。
4.至于partition过程,参见上图。
5.图一的划分方式,退出循环后i所指为第一个大于等于vot的元素,j所指为最后一个小于等于vot的元素。因此最后使a[j]与a[lb]交换即可让哨兵归至原位。

伪码:

void quickSort(int a[],int p,int r){
	if(p<r){
		int q=partition(a,p,r);
		quickSort(a,p,q-1);
		quickSort(a,q+1,r);
	}
}

代码:

import java.util.Scanner;

public class 快排递归 {
    
    
	static void swap(int a[],int i,int j) {
    
    
		int tmp = a[i];
		a[i]=a[j];
		a[j]=tmp;
	}
	static int partition(int a[],int lb,int ub) {
    
    
		//以下为图一划分方式
		int i=lb,j=ub+1;
		int vot=a[i];
		while(true) {
    
    
			while(i<ub&&a[++i]<vot);
			while(a[--j]>vot);
			if(i<j) swap(a,i,j);
			else break;
		}
		a[lb]=a[j];
		a[j]=vot;
		return j;
		//以下为图二划分方式
		/*int i=lb,j=ub;
		int vot=a[i];
		while(true) {//一旦j==i就终止循环。因为左游标左侧、右游标右侧代表已处理妥当的元素。而左右游标之所指,代表要互相比较的两个元素。相遇时,游标左右已妥,而游标本身进行对比不会改变什么。因此结束。
			while(j>i&&a[j]>=vot) j--;
			if(j>i) {//加这个条件是筛掉,如,基准元素左侧全是比它小的。下同。
				a[i++]=a[j];
			}
			while(j>i&&a[i]<=vot) i++;
			if(j>i) {
				a[j--]=a[i];
			}
			if(!(j>i)) break;
		}
		a[i]=vot;
		return i;*/
	}
	static void quickSort(int a[],int lb,int ub) {
    
    
		int q=-1;
		if(ub>lb) {
    
    
			q=partition(a, lb, ub);
			quickSort(a, lb, q-1);
			quickSort(a, q+1, ub);
		}
		
	}
	public static void main(String args[]) {
    
    
		Scanner sc=new Scanner(System.in);
		int n=sc.nextInt();
		int a[]=new int[n];
		for(int i=0;i<n;i++) {
    
    
			a[i]=sc.nextInt();
		}
		quickSort(a, 0, n-1);
		for(int i=0;i<n;i++) {
    
    
			System.out.println(a[i]);
		}
	}
}

Guess you like

Origin blog.csdn.net/qq_42021845/article/details/106887000