目 錄
第9章 排序(上)
9.1 簡單排序(冒泡、插入)
1、前提
void X_Sort ( ElementType A[], int N )
- 大多數情況下,爲簡單起見,討論從小大的整數排序
- N是正整數
- 只討論基於比較的排序(> = < 有定義)
- 只討論內部排序
- 穩定性:任意兩個相等的數據, 排序前後的相對位置不發生改變
- 沒有一種排序是任何情況下 都表現最好的
ElemnetType:所排元素類型;N:元素個數。10萬數據量。
2、簡單排序(冒泡排序)
void Bubble_Sort( ElementType A[], int N ) {
for ( P=N-1; P>=0; P-- ) {
flag = 0;
for( i=0; i<P; i++ ) { /* 一趟冒泡 */
if ( A[i] > A[i+1] ) {
Swap(A[i], A[i+1]);
flag = 1; /* 標識發生了交換 */
}
}
if ( flag==0 )
break; /* 全程無交換 */
}
}
冒泡排序 優點:對 數組、鏈表,均可進行排序。
P=N-1:從最後的元素,開始往前比較。
對於7個數進行冒泡排序,最壞情況下需要進行的比較次數爲 21 .
3、簡單排序(插入排序)
void InsertionSort( ElementType A[], int N )
{ /* 插入排序 */
int P, i;
ElementType Tmp;
for ( P=1; P<N; P++ ) {
Tmp = A[P]; /* 取出未排序序列中的第一個元素*/
for ( i=P; i>0 && A[i-1]>Tmp; i-- )
A[i] = A[i-1]; /*依次與已排序序列中元素比較並右移*/
A[i] = Tmp; /* 放進合適的位置 */
}
}
P=1:初始手中 就有 1張牌。
給定初始序列{34, 8, 64, 51, 32, 21},冒泡排序和插入排序分別需要多少次元素交換才能完成?【冒泡9次,插入9次】
對一組包含10個元素的非遞減有序序列,採用插入排序排成非遞增序列,其可能的比較次數和移動次數分別是【45, 44】。
4、時間複雜度下界
序列{34, 8, 64, 51, 32, 21}中有多少逆序對?【9】
N:元素個數;I:逆序對個數。
9.2 希爾排序
void ShellSort( ElementType A[], int N )
{ /* 希爾排序 - 用Sedgewick增量序列 */
int Si, D, P, i;
ElementType Tmp;
/* 這裏只列出一小部分增量 */
int Sedgewick[] = {929, 505, 209, 109, 41, 19, 5, 1, 0};
for ( Si=0; Sedgewick[Si]>=N; Si++ );
/* 初始的增量Sedgewick[Si]不能超過待排序列長度 */
for ( D=Sedgewick[Si]; D>0; D=Sedgewick[++Si] )
for ( P=D; P<N; P++ ) { /* 插入排序*/
Tmp = A[P];
for ( i=P; i>=D && A[i-D]>Tmp; i-=D )
A[i] = A[i-D];
A[i] = Tmp;
}
}
希爾排序是穩定的。【錯誤】
9.3 堆排序
void Swap( ElementType *a, ElementType *b )
{
ElementType t = *a; *a = *b; *b = t;
}
void PercDown( ElementType A[], int p, int N )
{ /* 改編代碼4.24的PercDown( MaxHeap H, int p ) */
/* 將N個元素的數組中以A[p]爲根的子堆調整爲最大堆 */
int Parent, Child;
ElementType X;
X = A[p]; /* 取出根結點存放的值 */
for( Parent=p; (Parent*2+1)<N; Parent=Child ) {
Child = Parent * 2 + 1;
if( (Child!=N-1) && (A[Child]<A[Child+1]) )
Child++; /* Child指向左右子結點的較大者 */
if( X >= A[Child] ) break; /* 找到了合適位置 */
else /* 下濾X */
A[Parent] = A[Child];
}
A[Parent] = X;
}
void HeapSort( ElementType A[], int N )
{ /* 堆排序 */
int i;
for ( i=N/2-1; i>=0; i-- )/* 建立最大堆 */
PercDown( A, i, N );
for ( i=N-1; i>0; i-- ) {
/* 刪除最大堆頂 */
Swap( &A[0], &A[i] ); /* 見代碼7.1 */
PercDown( A, 0, i );
}
}
typedef struct HNode *Heap; /* 堆的類型定義 */
struct HNode {
ElementType *Data; /* 存儲元素的數組 */
int Size; /* 堆中當前元素個數 */
int Capacity; /* 堆的最大容量 */
};
typedef Heap MaxHeap; /* 最大堆 */
typedef Heap MinHeap; /* 最小堆 */
#define MAXDATA 1000 /* 該值應根據具體情況定義爲大於堆中所有可能元素的值 */
MaxHeap CreateHeap( int MaxSize )
{ /* 創建容量爲MaxSize的空的最大堆 */
MaxHeap H = (MaxHeap)malloc(sizeof(struct HNode));
H->Data = (ElementType *)malloc((MaxSize+1)*sizeof(ElementType));
//指向數組,下標從1開始,所以 是 MaxSize+1
H->Size = 0;
H->Capacity = MaxSize;
H->Data[0] = MAXDATA; /* 定義"哨兵"爲大於堆中所有可能元素的值*/
return H;
}
bool IsFull( MaxHeap H )
{
return (H->Size == H->Capacity);
}
bool Insert( MaxHeap H, ElementType X )
{ /* 將元素X插入最大堆H,其中H->Data[0]已經定義爲哨兵 */
int i;
if ( IsFull(H) ) {
printf("最大堆已滿");
return false;
}
i = ++H->Size; /* i指向插入後堆中的最後一個元素的位置 */
for ( ; H->Data[i/2] < X; i/=2 )
H->Data[i] = H->Data[i/2]; /* 上濾X */
H->Data[i] = X; /* 將X插入 */
return true;
}
#define ERROR -1 /* 錯誤標識應根據具體情況定義爲堆中不可能出現的元素值 */
bool IsEmpty( MaxHeap H )
{
return (H->Size == 0);
}
ElementType DeleteMax( MaxHeap H )
{ /* 從最大堆H中取出鍵值爲最大的元素,並刪除一個結點 */
int Parent, Child;
ElementType MaxItem, X;
if ( IsEmpty(H) ) {
printf("最大堆已爲空");
return ERROR;
}
MaxItem = H->Data[1]; /* 取出根結點存放的最大值 */
/* 用最大堆中最後一個元素從根結點開始向上過濾下層結點 */
X = H->Data[H->Size--]; /* 注意當前堆的規模要減小 */
for( Parent=1; Parent*2<=H->Size; Parent=Child ) {
Child = Parent * 2;
if( (Child!=H->Size) && (H->Data[Child]<H->Data[Child+1]) )
Child++; /* Child指向左右子結點的較大者 */
if( X >= H->Data[Child] ) break; /* 找到了合適位置 */
else /* 下濾X */
H->Data[Parent] = H->Data[Child];
}
H->Data[Parent] = X;
return MaxItem;
}
/*----------- 建造最大堆 -----------*/
void PercDown( MaxHeap H, int p )
{ /* 下濾:將H中以H->Data[p]爲根的子堆調整爲最大堆 */
int Parent, Child;
ElementType X;
X = H->Data[p]; /* 取出根結點存放的值 */
for( Parent=p; Parent*2<=H->Size; Parent=Child ) {
Child = Parent * 2;
if( (Child!=H->Size) && (H->Data[Child]<H->Data[Child+1]) )
Child++; /* Child指向左右子結點的較大者 */
if( X >= H->Data[Child] ) break; /* 找到了合適位置 */
else /* 下濾X */
H->Data[Parent] = H->Data[Child];
}
H->Data[Parent] = X;
}
void BuildHeap( MaxHeap H )
{ /* 調整H->Data[]中的元素,使滿足最大堆的有序性 */
/* 這裏假設所有H->Size個元素已經存在H->Data[]中 */
int i;
/* 從最後一個結點的父節點開始,到根結點1 */
for( i = H->Size/2; i>0; i-- )
PercDown( H, i );
}
有個堆其元素在數組中的序列爲:58,25,44,18,10,26,20,12。如果調用DeleteMax函數刪除最大值元素,請猜猜看:程序中的for循環剛退出時變量parent的值是多少?【6】
建堆時,最壞情況下需要挪動元素次數是等於樹中各結點的高度和。問:對於元素個數爲12的堆,其各結點的高度之和是多少?【10】
在堆排序中,元素下標從0開始。則對於下標爲i的元素,其左、右孩子的下標分別爲:【2i+1, 2i+2】
排序方法綜合比較
排序彙總(1)
#include <stdio.h>
#include <string.h>
#define MAXSIZE 100 /*參加排序元素的最大個數*/
/******************冒泡排序********************/
void maopao()
{
int nums[MAXSIZE];
int i, j, n, temp;
int comnum = 0, movnum = 0;
int num = 1;
printf("您已進入冒泡排序\n");
printf("請輸入排序序列長度:");
scanf("%d", &n);
printf("請輸入排序序列:");
for (i = 0; i < n; i++)
scanf("%d", &nums[i]);
for (i = 0; i < n - 1; i++)
{
for (j = 0; j < n - i - 1; j++)
{
comnum++;
if (nums[j] > nums[j + 1])
{
temp = nums[j];
nums[j] = nums[j + 1];
nums[j + 1] = temp;
movnum++;
}
}
printf("第%d趟排序結果:", num++);
for (j = 0; j < n; j++)
{
printf("%d ", nums[j]);
}
printf("\n");
}
printf("排序過程比較次數:%d\n排序過程移動次數:%d\n", comnum, movnum);
printf("\n");
return;
}
/************************************************/
/*****************折半插入排序*******************/
void zheban()
{
int nums[MAXSIZE];
int i, j, n, temp;
int low, high, middle;
int comnum = 0, movnum = 0;
int num = 1;
printf("您已進入折半插入排序\n");
printf("請輸入排序序列長度:");
scanf("%d", &n);
printf("請輸入排序序列:");
for (i = 0; i < n; i++)
{
scanf("%d", &nums[i]);
}
for (i = 1; i < n; i++)
{
low = 0; //有序數組的開頭下標
high = i - 1; //有序數組的末尾下標
temp = nums[i]; //要被插入的數
middle = 0;
//查找要被插入的下標
while (low <= high)
{
middle = (low + high) / 2;
if (temp < nums[middle])
{
high = middle - 1;
}
else
{
low = middle + 1;
}
comnum++;
}
//所有數右移,移完之後插入目標數
for (j = i; j > low; j--)
{
nums[j] = nums[j - 1];
}
//交換nums[i]與nums[low]的位置
nums[low] = temp;
movnum++;
printf("第%d趟排序結果:", num++);
for (j = 0; j < n; j++)
{
printf("%d ", nums[j]);
}
printf("\n");
}
printf("排序過程比較次數:%d\n排序過程移動次數:%d\n", comnum, movnum);
printf("\n");
return;
}
/************************************************/
/*******************希爾排序*********************/
void shell()
{
int i, j, k, n, dk, temp;
int nums[MAXSIZE];
int comnum = 0, movnum = 0;
int num = 1;
printf("您已進入希爾排序\n");
printf("請輸入排序序列長度:");
scanf("%d", &n);
printf("請輸入排序序列:");
for (i = 0; i < n; i++)
{
scanf("%d", &nums[i]);
}
for (dk = n / 2; dk > 0; dk = dk / 2)
{
for (i = 0; i < dk; i++)
{
for (j = i + dk; j < n; j = j + dk)
{ //單獨一次的插入排序
if (nums[j] < nums[j - dk])
{
temp = nums[j]; //哨兵
k = j - dk;
while (k >= 0 && nums[k] > temp)
{
nums[k + dk] = nums[k];
k = k - dk;
}
nums[k + dk] = temp;
movnum++;
}
comnum++;
}
}
printf("第%d趟排序結果:", num++);
for (i = 0; i < n; i++)
{
printf("%d ", nums[i]);
}
printf("\n");
}
printf("排序過程比較次數:%d\n排序過程移動次數:%d\n", comnum, movnum);
printf("\n");
return;
}
/************************************************/
/*******************快速排序*********************/
int CN = 0;
int MN = 0;
int T = 1;
void Fswap(int nums[], int i, int j)
{
int temp;
temp = nums[i];
nums[i] = nums[j];
nums[j] = temp;
MN++;
}
int partition(int nums[], int low, int high, int n)
{
int i;
int pivotkey;
pivotkey = nums[low];
while (low < high) //以pivoekey爲軸,將大於它的放在後邊,小於它的放在前面
{
while (low < high && nums[high] >= pivotkey) //條件判斷 low < high
{
high--;
CN++;
}
Fswap(nums, low, high);
while (low < high && nums[low] <= pivotkey)
{
low++;
CN++;
}
Fswap(nums, low, high);
printf("第%d趟排序結果:", T++);
for (i = 0; i < n; i++)
{
printf("%d ", nums[i]);
}
printf("\n");
}
return low; //返回樞軸所在位置
}
void quickSort(int nums[], int low, int high, int n)
{
int pivot;
if (low < high)
{
pivot = partition(nums, low, high, n); //將nums[]一分爲二
quickSort(nums, low, pivot - 1, n); //對低子表遞歸排序
quickSort(nums, pivot + 1, high, n); //對高子表遞歸排序
}
}
void kuaipai()
{
int i, n;
int nums[MAXSIZE];
printf("您已進入快速排序\n");
printf("請輸入排序序列長度:");
scanf("%d", &n);
printf("請輸入排序序列:");
CN = 0;
MN = 0;
T = 1;
for (i = 0; i < n; i++)
{
scanf("%d", &nums[i]);
}
quickSort(nums, 0, n - 1, n);
printf("排序過程比較次數:%d\n排序過程移動次數:%d\n", CN, MN);
printf("\n");
return;
}
/************************************************/
/********************堆排序**********************/
int HCN = 0;
int HMN = 0;
int H = 1;
void HeapAdjust(int nums[], int s, int n)
{
int i, j;
int temp;
for (i = s; 2 * i + 1 < n; i = j)
{
j = 2 * i + 1;
if ((j < n - 1) && (nums[j] < nums[j + 1]))
{
j++;
HCN++;
}
if (nums[i] < nums[j])
{
temp = nums[i];
nums[i] = nums[j];
nums[j] = temp;
HCN++;
HMN++;
}
else
break;
}
}
//堆排序
void HeapSort(int nums[], int n)
{
int i, j;
int temp;
for (i = n / 2 - 1; i >= 0; i--)
{
HeapAdjust(nums, i, n);
printf("第%d趟排序結果:", H++);
for (j = 0; j < n; j++)
{
printf("%d ", nums[j]);
}
printf("\n");
}
for (i = n - 1; i > 0; i--)
{
temp = nums[i];
nums[i] = nums[0];
nums[0] = temp;
HMN++;
HeapAdjust(nums, 0, i);
printf("第%d趟排序結果:", H++);
for (j = 0; j < n; j++)
{
printf("%d ", nums[j]);
}
printf("\n");
}
}
void duipai()
{
int i, n;
int nums[MAXSIZE];
printf("您已進入堆排序\n");
printf("請輸入排序序列長度:");
scanf("%d", &n);
printf("請輸入排序序列:");
HMN = 0;
HCN = 0;
H = 1;
for (i = 0; i < n; i++)
{
scanf("%d", &nums[i]);
}
HeapSort(nums, n);
printf("排序過程比較次數:%d\n排序過程移動次數:%d\n", HCN, HMN);
printf("\n");
return;
}
/************************************************/
/*****************直接插入排序*******************/
void zhicha()
{
int nums[MAXSIZE];
int i, j, n;
int temp;
int comnum = 0, movnum = 0;
int num = 1;
printf("您已進入直接插入排序\n");
printf("請輸入排序序列長度:");
scanf("%d", &n);
printf("請輸入排序序列:");
for (i = 0; i < n; i++)
{
scanf("%d", &nums[i]);
}
for (i = 1; i < n; i++)
{
if (nums[i] < nums[i - 1])
{
temp = nums[i];
for (j = i - 1; j >= 0; j--)
{
if (temp < nums[j])
{
nums[j + 1] = nums[j];
comnum++;
}
else
{
break;
comnum++;
}
}
nums[j + 1] = temp;
movnum++;
}
else
{
comnum++;
continue;
}
printf("第%d趟排序結果:", num++);
for (j = 0; j < n; j++)
{
printf("%d ", nums[j]);
}
printf("\n");
}
printf("排序過程比較次數:%d\n排序過程移動次數:%d\n", comnum, movnum);
printf("\n");
}
/************************************************/
/*****************簡單選擇排序*******************/
void jiandan()
{
int nums[MAXSIZE];
int i, j, n;
int temp, t;
int comnum = 0, movnum = 0;
int num = 1;
printf("您已進入簡單選擇排序\n");
printf("請輸入排序序列長度:");
scanf("%d", &n);
printf("請輸入排序序列:");
for (i = 0; i < n; i++)
{
scanf("%d", &nums[i]);
}
for (i = 0; i < n; i++)
{
temp = nums[i];
t = i;
for (j = i + 1; j < n; j++)
{
if (nums[j] < temp)
{
temp = nums[j];
t = j;
}
comnum++;
}
temp = nums[i];
nums[i] = nums[t];
nums[t] = temp;
movnum++;
printf("第%d趟排序結果:", num++);
for (j = 0; j < n; j++)
{
printf("%d ", nums[j]);
}
printf("\n");
}
printf("排序過程比較次數:%d\n排序過程移動次數:%d\n", comnum, movnum);
printf("\n");
}
/************************************************/
/********************主函數**********************/
int main()
{
int n;
while (1)
{
printf(" 主菜單\n");
printf("請選擇排序算法\n");
printf("冒泡排序法 1\n");
printf("折半插入排序法 2\n");
printf("希爾排序法 3\n");
printf("快速排序法 4\n");
printf("堆排序法 5\n");
printf("直接插入排序法 6\n");
printf("簡單選擇排序法 7\n");
printf("退出 0\n");
scanf("%d", &n);
switch (n)
{
case 1:
maopao();
continue;
case 2:
zheban();
continue;
case 3:
shell();
continue;
case 4:
kuaipai();
continue;
case 5:
duipai();
continue;
case 6:
zhicha();
continue;
case 7:
jiandan();
continue;
default:
break;
}
if (n == 0)
break;
}
return 0;
}
排序彙總(2)
#include <iostream>
#include <stdio.h>
#include <stdlib.h>
using namespace std;
#ifndef SQLIST_H_INCLUDED
#define SQLIST_H_INCLUDED
#define MAXSIZE 20 //順序表的最大長度
typedef int KeyType; //定義關鍵字類型爲整型
typedef int InfoType;
typedef struct
{
KeyType key;
InfoType otherinfp;
} RedType;
typedef struct
{
RedType r[MAXSIZE + 1]; //r[0]是哨兵的位置,防止數組越界
int length;
} SqList;
void menu();
void InSqList(SqList &sq);
void InsertSort(SqList &sq);
void OutPrintSqList(SqList &L);
void BInsertSort(SqList &L); //折半插入排序
void ShellSort(SqList &L, int dk[], int t); //希爾排序
void ShellInsert(SqList &L, int dk); //做一趟增量爲dk的希爾排序
void BubbleSort(SqList &L); //冒泡排序
int PartitionQ(SqList &L, int low, int high); //一趟快速排序,返回樞軸位置
void QSort(SqList &L, int low, int high);
void QuickSort(SqList &L); //快速排序
void SelectSort(SqList &L); //簡單選擇排序
//堆排序
void HeapAdjust(SqList &L, int s, int m);
void CreateHeap(SqList &L);
void HeapSort(SqList &L);
//歸併排序
void Merge(SqList R, SqList &T, int low, int mid, int high);
void Msort(SqList R, SqList &T, int low, int high);
void MergeSort(SqList &L);
#endif // SQLIST_H_INCLUDED
void menu()
{
printf("---------------------------\n");
printf("1---直接插入排序\n");
printf("2---折半插入排序\n");
printf("3---希爾排序\n");
printf("4---冒泡排序\n");
printf("5---快速排序\n");
printf("6---簡單選擇排序\n");
printf("7---堆排序\n");
printf("8---歸併排序\n");
printf("0----退出\n");
printf("----------------------------\n");
}
void InSqList(SqList &sq)
{
int i = 1;
sq.length = 0;
printf("請輸入8個關鍵字:\n");
for (; i <= 8; i++)
{
printf("請輸入第%d個關鍵字:\n", i);
scanf("%d", &sq.r[i].key);
sq.r[i].otherinfp = i;
sq.length++;
}
}
void OutPrintSqList(SqList &sq)
{
int i;
printf("******************\n");
for (i = 1; i <= sq.length; i++)
printf("%d ", sq.r[i].key);
printf("\n");
}
void InsertSort(SqList &L)
{
int i, j;
for (i = 2; i <= L.length; i++)
{
if (L.r[i].key < L.r[i - 1].key)
{
L.r[0] = L.r[i];
L.r[i] = L.r[i - 1];
for (j = i - 2; L.r[0].key < L.r[j].key; j--)
L.r[j + 1] = L.r[j];
L.r[j + 1] = L.r[0];
}
}
}
void BInsertSort(SqList &L)
{
int i, j, low, high, mid;
for (i = 2; i <= L.length; i++)
{
L.r[0] = L.r[i];
low = 1;
high = i - 1;
while (low <= high)
{
mid = (low + high) / 2;
if (L.r[0].key < L.r[mid].key)
high = mid - 1;
else
low = mid + 1;
}
for (j = i - 1; j >= high + 1; --j)
L.r[j + 1] = L.r[j];
L.r[j + 1] = L.r[0];
}
}
void ShellSort(SqList &L, int dk[], int t) //希爾排序
{
int k;
for (k = 0; k < t; k++)
ShellInsert(L, dk[k]);
}
//做一趟增量爲dk的希爾排序
void ShellInsert(SqList &L, int dk)
{
int i, j;
for (i = dk + 1; i <= L.length; i++)
{
if (L.r[i].key < L.r[i - dk].key) //需要將L.r[i]插入到有序增量子表
{
L.r[0] = L.r[i]; //暫存在L.r[0]
for (j = i - dk; j > 0 && L.r[0].key < L.r[j].key; j -= dk) //記錄後移,直到找到插入位置
L.r[j + dk] = L.r[j];
L.r[j + dk] = L.r[0]; //將r[0]即原r[i],插入到正確位置
}
}
}
//冒泡排序
void BubbleSort(SqList &L)
{
int j, i, flag = 1;
RedType t;
j = L.length - 1;
while (j > 0 && flag == 1)
{
flag = 0;
for (i = 1; i <= j; i++)
{
if (L.r[i + 1].key < L.r[i].key)
{
flag = 1;
t = L.r[i];
L.r[i] = L.r[i + 1];
L.r[i + 1] = t;
}
}
j--;
}
}
//快速排序
int PartitionQ(SqList &L, int low, int high) //一趟快速排序,返回樞軸位置
{
//1.選樞軸
int pivotkey = L.r[low].key;
L.r[0] = L.r[low];
while (low < high)
{
while (low < high && pivotkey <= L.r[high].key)
high--;
L.r[low] = L.r[high];
while (low < high && pivotkey >= L.r[low].key)
low++;
L.r[high] = L.r[low];
}
L.r[low] = L.r[0];
return low;
}
void QSort(SqList &L, int low, int high)
{
int pivotloc;
if (low < high)
{
pivotloc = PartitionQ(L, low, high); //以樞軸爲支點將表分爲兩部分,返回數軸的位置
QSort(L, low, pivotloc - 1); //遞歸左子表
QSort(L, pivotloc + 1, high); //遞歸右子表
}
}
void QuickSort(SqList &L)
{
QSort(L, 1, L.length);
}
//簡單選擇排序
void SelectSort(SqList &L)
{
int i, j, k;
RedType t;
for (i = 1; i < L.length; i++)
{
k = i;
for (j = i + 1; j <= L.length; j++)
if (L.r[j].key < L.r[k].key)
k = j;
if (k != i)
{
t = L.r[i];
L.r[i] = L.r[k];
L.r[k] = t;
}
}
}
//堆排序 調整堆
void HeapAdjust(SqList &L, int s, int m)
{
RedType rc;
int j;
rc = L.r[s];
for (j = 2 * s; j <= m; j *= 2)
{
while (j < m && L.r[j].key < L.r[j + 1].key)
j++; //s與左右孩子較大的比較,這是堆排序的性質決定的
if (rc.key >= L.r[j].key)
break;
L.r[s] = L.r[j];
s = j;
}
L.r[s] = rc;
}
//建初堆
void CreateHeap(SqList &L)
{
int n = L.length;
int i;
for (i = n / 2; i > 0; i--)
HeapAdjust(L, i, n);
}
//堆排序
void HeapSort(SqList &L)
{
int i;
RedType x;
CreateHeap(L);
for (i = L.length; i > 0; i--)
{
x = L.r[1];
L.r[1] = L.r[i];
L.r[i] = x;
HeapAdjust(L, 1, i - 1);
}
}
//歸併排序
void Merge(SqList R, SqList &T, int low, int mid, int high)
{
int i, j, k;
i = low;
j = mid + 1;
k = low;
while (i <= mid && j <= high)
{
if (R.r[i].key <= R.r[j].key)
T.r[k++] = R.r[i++];
else
T.r[k++] = R.r[j++];
}
while (i <= mid)
T.r[k++] = R.r[i++];
while (j <= high)
T.r[k++] = R.r[j++];
}
void Msort(SqList R, SqList &T, int low, int high)
{
int mid;
SqList S; //輔助存儲空間
if (low == high)
T.r[low] = R.r[low];
else
{
mid = (low + high) / 2;
Msort(R, S, low, mid);
Msort(R, S, mid + 1, high);
Merge(S, T, low, mid, high);
}
}
void MergeSort(SqList &L)
{
Msort(L, L, 1, L.length);
}
int main()
{
SqList sq;
int index;
int dk[] = {5, 3, 1};
while (1)
{
menu();
printf("請輸入排序類型:\n");
scanf("%d", &index);
if (!index)
return 0;
//輸入
InSqList(sq);
//輸出
OutPrintSqList(sq);
switch (index)
{
case 1:
InsertSort(sq); //直接插入排序
//輸出
break;
case 2:
BInsertSort(sq); //折半插入排序
break;
case 3:
ShellSort(sq, dk, 3);
break;
case 4:
BubbleSort(sq);
break;
case 5:
QuickSort(sq);
break;
case 6:
SelectSort(sq);
break;
case 7:
HeapSort(sq);
break;
case 8:
MergeSort(sq);
break;
}
printf("排序後:\n");
//輸出
OutPrintSqList(sq);
printf("*************第4個49之前的位序是:%d**************\n", sq.r[4].otherinfp);
system("pause");
}
return 0;
}