目录
前言
排序分为内排序和外排序,内排序是指排序时不涉及数据的内、外存交换。本章讨论的是内排序。内排序主要有8种方式,它们各有优劣。
一、排序的基本概念
1.排序的定义
所谓排序,就是整理表中的元素,使之按照关键字递增或递减有序排列。在默认情况下所有的排序均指的是递增排序。
2.内排序的分类
根据内排序算法是否基于关键字的比较,将内排序算法分为基于比较的排序算法和不基于比较的排序算法。插入排序、交换排序、选择排序和归并排序都是基于比较的排序算法,而基数排序则是不基于比较的排序算法。
3.排序的稳定性
当待排序的表中存在多个关键字相同的元素,经过排序后这些具有相同关键字的元素之间的相对次序保持不变,则称这种排序方法是稳定的。反之,如果这些元素的相对次序改变了,则称这种排序方法是不稳定的。
4.有序区与无序区
在排序过程中的某一时刻R被划分为两个区间,前面的子区间是已经排好序的,称作有序区,后面的是待排序的部分,称为无序区
5.排序数据的组织
在讨论排序算法时,以顺序表作为排序数据的存储结构,假设关键字为int类型,其元素类型定义如下:
public class SortType {
int key; //存放关键字
String data; //存放其他数据
public SortType(int key){
this.key = key;
}
}
设计用于内排序的SortClass如下:
public class SortClass {
final int MAXSIZE = 100; //最多元素的个数
SortType[] R; //存放排序的元素
int num; //表中实际元素的个数
/**
* 交换i和j
* @param i
* @param j
*/
public void swap(int i,int j){
SortType tmp;
tmp = R[i];
R[i] = R[j];
R[j] = tmp;
}
/**
* 由关键字序列a构造顺序表R
* @param a
*/
public void creatR(int[]a){
R = new SortType[MAXSIZE];
for (int i = 0; i < a.length; i++) {
R[i] = new SortType(a[i]);
}
num = a.length;
}
/**
* 构造用于堆排序的R
* @param a
*/
public void creatR_1(int[]a){
R = new SortType[MAXSIZE];
for (int i = 0; i < a.length; i++) {
R[i+1] = new SortType(a[i]);
}
num = a.length;
}
/**
* 输出顺序表R
*/
public void display(){
for (int i = 0; i < num; i++) {
System.out.print(R[i].key+" ");
}
System.out.println();
}
/**
* 输出用于堆排序的R
*/
public void display_1(){
for (int i = 1; i <= num; i++) {
System.out.print(R[i].key+" ");
}
System.out.println();
}
}
二、插入排序
插入排序的基本思想是每次将一个待排序的元素按其关键字大小插入前面已经排好序的子表中的适当位置
1.直接插入排序
直接插入排序的每趟操作是将当前无序区的开头元素插入有序区中适当位置,从而扩大有序区减少无序区。这种方法通常称为增量法,因为它每次使有序区增加一个元素。经过n-1趟后无序区变空。
其过程为:先将无序区头元素R[i]暂时放入tmp中,用j在有序区从后往前找,凡是大于tmp的元素均后移一个位置,指到找到某个小于或等于tmp的元素为止,再将tmp放在它的后面
public void insertSort(){
SortType tmp;
int j;
for (int i = 1; i < num; i++) { //从R[1]开始
if (R[i].key < R[i - 1].key) { //当反序时才执行,可以减少运行次数
tmp = R[i]; //取出无序区第一个元素
j = i - 1; //有序区的末尾
while (j >= 0 && tmp.key < R[j].key) {
R[j + 1] = R[j]; //将所有比tmp大的元素后移
j--;
}
R[j + 1] = tmp; //在j+1处插入tmp
}
}
}
2.折半插入排序
折半查找是先在有序区中用折半查找方法找到插入位置,再通过移动元素经行插入。折半插入排序又称为二分插入排序
public void halfSort(){
SortType tmp;
int left;
int right;
int mid;
for (in