排序方式------>希尔排序,堆排序

6.希尔排序
希尔排序类似于插入排序,是一种缩小增量的排序。
①首先设置整个数组的步长,设置步长为数组的一半;
②继续将步长设置为原步长的一半;
③当步长为一时,结束。

代码:(以数组长度为10为例)

public static void main(String[] args) {
		int[] arr=new int[] {5,9,2,1,7,6,3,4,8,0};
		sort(arr);
		System.out.println(Arrays.toString(arr));
		
	}
	//逐步写出整个希尔排序
	public static void sort(int[] arr) {
		//将10个数据划分为五组,定义一个i代指步长
		for(int i=5;i<arr.length;i++) {
			//j应该指向数组当中的第一个元素
			for(int j=i-5; j>=0;j-=5) {
				if(arr[j] >arr[j+5]) {
					int temp=arr[j];
					arr[j]=arr[j+5];
					arr[j+5]=temp;
				}
				
			}
			
		}
		//将10个数据划分为2组,定义一个i代指步长
		for(int i=2;i<arr.length;i++) {
			//j应该指向数组当中的第一个元素
			for(int j=i-2; j>=0;j-=2) {
				if(arr[j] >arr[j+2]) {
					int temp=arr[j];
					arr[j]=arr[j+2];
					arr[j+2]=temp;
				}	
			}	
		}
		//将10个数据划分为1组,定义一个i代指步长
		for(int i=1;i<arr.length;i++) {
			//j应该指向数组当中的第一个元素
			for(int j=i-1; j>=0;j-=1) {
				if(arr[j] >arr[j+1]) {
					int temp=arr[j];
					arr[j]=arr[j+1];
					arr[j+1]=temp;
				}	
			}	
		}
		
	}

总体来看就是

public static void shell(int[] arr) {
		//grp表示步长
		for(int grp =arr.length/2;grp>0;grp/=2) {
			//将10个数据划分为2组,定义一个i代指步长
			for(int i=grp;i<arr.length;i++) {
				//j应该指向数组当中的第一个元素
				for(int j=i-grp; j>=0;j-=grp) {
					if(arr[j] >arr[j+grp]) {
						int temp=arr[j];
						arr[j]=arr[j+grp];
						arr[j+grp]=temp;
					}	
				}	
			}
		}	
	}

结果图
在这里插入图片描述
7.堆排序(大、小顶堆)
堆排序运用到完全二叉树(完全二叉树:从上到下,从左到右依次铺满)
堆排序是利用了平衡二叉树的一些特点来实现完全二叉树
堆排序的基本思想:
① 利用平衡二叉树的特点构建大、小顶堆;
② 将堆顶元素和最后一个元素进行位置互换;
③ 重复前两个步骤。
堆排序的步骤:
一、(arr.length-1)/2:最后一个拥有子树的节点
二、定义一个指针指向左右子树当中最大的一个
三、最大的子节点和父节点进行对比,如果子节点大于父节点,交换位置
四、将堆顶元素和最后一个元素进行位置互换

代码:

public class dui {

	public static void main(String[] args) {
		int[] arr=new int[] {5,9,2,1,7,6,3,4,8,0};
		sort(arr);
		System.out.println(Arrays.toString(arr));
	}
	
	public static void sort(int [] arr) {
		//构建大顶堆
		for(int i=(arr.length)/2;i>=0;i--) {
			adjustHeap(arr,i,arr.length);
		}
		//将堆顶元素和最后一个元素进行位置互换
		for(int i=arr.length-1;i>0;i--) {
			int temp=arr[i];
			arr[i]=arr[0];
			arr[0]=temp;
			//重新构建大顶堆
			adjustHeap(arr,0,i);
		}
	}
	
	public static void adjustHeap(int[] arr,int parent,int length){
		int temp=arr[parent];
		//定义左孩子,找到左孩子
		int leftChild=2*parent+1;
		while(leftChild<length) {
			int rightChild=leftChild+1;
			if(rightChild<length && arr[leftChild]<arr[rightChild]) {
				leftChild=rightChild;
			}
			//判断父节点的值是否大于子节点的值
			if(temp>=arr[leftChild]) {
				break;
			}
			//否则子节点到父结点中去
			arr[parent]=arr[leftChild];
			//将选下来的原来父结点的值再次进行筛选
			
			parent=leftChild;
			leftChild=2*leftChild+1;
			
			
		}
		arr[parent]=temp;
	}

猜你喜欢

转载自blog.csdn.net/weixin_53954158/article/details/119302543