package com.abuge;
/**
* 希尔排序:
* 实质:分组插入排序,又称为缩小增量排序
* 思想:
* 先将整个待排元素序列分割成若干个子序列(由相隔某个"增量"的元素组成的)分别进行直接插入排序,待整个序列中的元素基本有序(增量足够小)时,再对全体元素进行直接插入排序。
* 因为直接插入排序是在基本有序的情况下(接近最好情况)效率是很高的。
* 第一种方法(把一组元素从开始比较到最后)
* 步骤:
* 1、设定分组增量初值,即为gap = n/2(n为元素个数),则每次以gap = gap / 2循环
* 2、按组排序即0-> gap-> gap + gap->...
* 1-> 1 + gap->...
* .
* .
* .
* gap-1 -> gap + gap - 1->...
* 3、如果后面的比前面的小,则交换顺序(升序排列)
* 4、循环交换到0位置或者比要比较元素小的元素时,将元素放在其后
*
*
* 第二种方法(从第gap个元素开始,每个元素与自己组内的元素进行比较,交替进行)
* 步骤:
* 1、设定分组增量初值,即为gap = n/2(n为元素个数),则每次以gap = gap / 2循环
* 2、从gap开始,进行组内比较,如果与同组元素的前一个无须交换,则比较下一组,从而实现了交替比较
* 3、比较过程中如果后面的比前面的小,则交换顺序(升序排列)
* 4、循环交换到0位置或者比要比较元素小的元素时,将元素放在其后
*
*
* 第三种方法(从第gap个元素开始,每个元素与自己组内前面的元素进行比较,交替进行)
* 步骤:
* 1、设定分组增量初值,即为gap = n/2(n为元素个数),则每次以gap = gap / 2循环
* 2、从gap开始,进行组内比较,如果与同组元素的前一个无须交换,则比较下一组,从而实现了交替比较
* 3、交换符合条件的元素
* @author AbuGe
*
*/
public class ShellSort
{
//第一种方法
public static void shellSort_1(int[] a, int n)
{
//设定循环变量,和步进增量
int i;
int j;
int gap;
for(gap = n / 2; gap > 0; gap = gap / 2)//设定步进增量
{
for(i = 0; i < gap; i++)//按组排序
{
for(j = i + gap; j < n; j = j + gap)
{
if(a[j] < a[j - gap])
{
int tmp = a[j];
int k = j - gap;
//循环比较
while(k >= 0 && a[k] > tmp)
{
a[k + gap] = a[k];
k -= gap;
}
a[k + gap] = tmp;
}
}
}
}
}
//第二种方法
public static void shellSort_2(int[] a, int n)
{
//设定循环变量,和步进增量
int i;
int gap;
for(gap = n / 2; gap > 0; gap = gap / 2)//设定步进增量
{
for(i = gap; i < n; i++)//循环增量为1,而第一个循环增量为gap
{
if(a[i] < a[i - gap])
{
int tmp = a[i];
int k = i - gap;
while(k >= 0 && a[k] > tmp)
{
a[k + gap] = a[k];
k -= gap;
}
a[k + gap] = tmp;
}
}
}
}
//第三种方法
public static void shellSort_3(int[] a, int n)
{
//设定循环变量,和步进增量
int i;
int j;
int gap;
for(gap = n / 2; gap > 0; gap = gap / 2)//设定步进增量
{
for(i = gap; i < n; i++)//循环增量为1,而第一个循环增量为gap
{
for(j = i - gap; j >= 0 && a[j] > a[j + gap]; j-= gap)
{
swap(a, j, j + gap);
}
}
}
}
public static void swap(int[]a , int x, int y)
{
int tmp = a[x];
a[x] = a[y];
a[y] = tmp;
}
public static void main(String[] args)
{
int[] a = {1, 13 , 11, 10, 6, 5, 8, 7};
int n = a.length;
System.out.print("排序前:");
for(int i : a)
{
System.out.print(i + " ");
}
System.out.println();
//shellSort_1(a, n);
//shellSort_2(a, n);
shellSort_3(a, n);
System.out.print("排序后:");
for(int i : a)
{
System.out.print(i + " ");
}
}
}
阿布学排序之希尔排序
最新推荐文章于 2014-07-16 21:44:19 发布