Java实现各种排序算法:选择排序,插入排序,冒泡排序,快速排序,归并排序,希尔排序,堆排序

本文详细介绍了五种主要的排序算法:简单选择排序、插入排序、冒泡排序、归并排序和快速排序,以及希尔排序和堆排序。每种算法都有详细的解释和对应的Java代码实现,帮助读者深入理解各种排序算法的工作原理。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

package sort;

public class Solution {
	
	/*
	 * 简单选择排序
	 */
	public void selectSort(int[] array) {
		for(int i=0; i<array.length - 1; i++) {
			for(int j=i+1; j<array.length; j++) {
				if(array[j] < array[i]) {
					int tmp = array[i];
					array[i] = array[j];
					array[j] = tmp;
				}
			}
		}
	}
	
	/*
	 * 简单插入排序
	 */
	public void insertSort(int[] array) {
		for(int i=1; i<array.length; i++) {
			for(int j=0; j<i; j++) {
				if(array[i] <= array[j]) {
					int tmp = array[i];
					for(int k=i-1; k>=j; k--) {
						array[k+1] = array[k];
					}
					array[j] = tmp;
					break;
				}
			}
		}
	}
	
	/*
	 * 冒泡排序
	 */
	public void bubbleSort(int[] array) {
		for(int i = 0; i < array.length - 1; i++) {	//冒泡length - 1次,第一个元素不用冒泡
			boolean continueFlag = false;	//优化一下,如果某一次冒泡没有发生交换,后面的冒泡就不用了
			for(int j = 0; j < array.length - 1 - i; j++) {
				if(array[j] > array[j+1]) {
					int tmp = array[j];
					array[j] = array[j + 1];
					array[j + 1] = tmp;
					continueFlag = true;
				}
			}
			if(continueFlag == false) {
				break;
			}
		}
	}
	
	/*
	 * 归并排序驱动程序
	 */
	public void mergeSort(int[] array) {
		mergeSort(array, 0, array.length - 1);
		
	}
	//归并排序主程序
	private void mergeSort(int[] array, int start, int end) {
		if(start == end)
			return;
		int mid = (start + end) / 2;
		mergeSort(array, start, mid);
		mergeSort(array, mid + 1, end);
		merge(array, start, end);
	}
	//合并两个有序数组,变成一个有序数组
	private void merge(int[] array, int start, int end) {
		int mid = (start + end) / 2;	//两数组的分界点
		int leftLength = mid - start + 1;
		int rightLength = end - mid;
		int[] leftArray = new int[leftLength];
		int[] rightArray = new int[rightLength];
		
		//从原数组中提取出左右数组
		for(int i = 0, k = start; i < leftLength; i++, k++) {
			leftArray[i] = array[k];
		}
		for(int i = 0, k = mid + 1; i < rightLength; i++, k++) {
			rightArray[i] = array[k];
		}
		
		int i = 0, j = 0, k = start;
		while(i < leftLength && j < rightLength) {
			if(leftArray[i] < rightArray[j]) {
				array[k] = leftArray[i];
				i++;
			}
			else {
				array[k] = rightArray[j];
				j++;
			}
			k++;
		}
		//把剩下的数组接上
		while(i < leftLength) {
			array[k] = leftArray[i];
			i++;
			k++;
		}
		while(j < rightLength) {
			array[k] = rightArray[j];
			j++;
			k++;
		}
	}
	
	/*
	 * 快速排序驱动程序
	 */
	public void quickSort(int[] array) {
		quickSort(array, 0, array.length - 1);
	}
	//快速排序主程序
	private void quickSort(int[] array, int start, int end) {
		if(start >= end) {
			return;
		}
		int i = start, j = end;	
		int index = array[i];	//默认数组第一个元素为基准
		while(i < j) {
			while(i < j && array[j] >= index) {
				j--;
			}
			if(i < j) {
				array[i] = array[j];
				i++;
			}
			
			while(i < j && array[i] < index) {
				i++;
			}
			if(i < j) {
				array[j] = array[i];
				j--;
			}
		}
		array[i] = index;
		
		quickSort(array, start, i - 1);
		quickSort(array, i + 1, end);
	}
	
	/*
	 * 希尔排序
	 */
	public void shellSort(int[] array) {
		for(int h = array.length / 2; h > 0; h /= 2) {
			//每个h对应的排序都是插入排序
			for(int i = h; i < array.length; i++) {
				int tmp = array[i];
				int j;
				for(j = i - h; j >= 0; j -= h) {
					if(array[j] > tmp) {
						array[j + h] = array[j];
					}
					else {
						break;
					}
				}
				array[j + h] = tmp;
			}
		}
	}
	
	/*
	 * 堆排序
	 */
	public void heapSort(int[] array) {
		//建大顶堆
		//从最后一个非叶子结点开始,从左往右,从下往上,依次以该非叶子结点为二叉树根,建立大顶堆
		for(int i = array.length/2 -1; i>=0; i--) {	//array.length/2 -1是最后一个非叶子结点
			adjustHeap(array, i, array.length);
		}
		
		//堆排序
		int cur_length = array.length;
		for(int i = 0; i < array.length - 1; i++) {	//摘除最大元素的次数
			//交换堆顶和堆最后一个元素
			int tmp = array[0];
			array[0] = array[cur_length - 1];
			array[cur_length - 1] = tmp;
			//“删除”最后一个元素
			cur_length--;
			//调整剩下的堆,使之重新成为大顶堆
			//只有根结点所在的二叉树不满足大顶堆,其他叶子结点都满足,所以只用调整根结点
			adjustHeap(array, 0, cur_length);	
		}
	}
	//调整堆为最大堆
	public void adjustHeap(int[] array, int root, int length) {
		int tmp = array[root];
		for(int i = root * 2 + 1; i < length; i = i * 2 + 1) {//root * 2 + 1是root的左孩子
			//i指向两个孩子中的较大者
			//i + 1 < length非常重要!,不然不会报错,而是把已经“删除”的元素引入
			if(i + 1 < length && array[i + 1] > array[i]) {	
				i++;
			}
			if(tmp < array[i]) {
				array[root] = array[i];
				root = i;	//	不用交换,下次循环以i作为新的root
			}
			else {
				break;
			}
		}
		//等结束循环,把tmp放到最终的root上
		array[root] = tmp;
	}
	
	/*
	 * 输出数组
	 */
	public void printArray(int[] array) {
		for(int item : array) {
			System.out.print(item + " ");
		}
		System.out.println();
	}
}

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值