數據結構排序的基本操作的實現

一、實驗目的

(1)掌握各種排序算法的基本思想;
(2)掌握各種排序算法的實現方法。

二、實驗內容

對一組數據進行排序,可選擇直接插入排序、折半插入排序、希爾排序、冒泡排序、快速排序、簡單選擇排序、堆排序和2-路歸併排序算法實現。
要求:設計菜單,根據菜單提示進行操作。

三、算法代碼

#include <iostream>
#include <iomanip>
#include <stdlib.h>
#include <time.h>
#include <cmath>
using namespace std;
#define MAXSIZE 10
typedef int KeyType;
typedef int InfoType;
typedef struct {
	KeyType key;
	InfoType otherinfo;
} RedType;
typedef struct {
	RedType r[MAXSIZE + 1];
	int length;
} SqList;

//打印
void print(SqList &t) {
	for (int i = 1; i <= t.length; i++) {
		if ((i - 1) % 10 == 0)
			cout << endl;
		cout <<" "<< t.r[i].key;
	}
	cout << endl;
}

//產生隨機數
void producerandom(SqList &t) {
	srand(time(NULL));
	for (int i = 1; i <= MAXSIZE; i++)
		t.r[i].key = rand() % 100;
	t.length = MAXSIZE;
	print(t);
}

//直接插入排序
void InsertSort(SqList &t) {
	for (int i = 2; i <= t.length; i++) {
		if (t.r[i].key < t.r[i - 1].key) {
			int j;
			t.r[0] = t.r[i];
			t.r[i] = t.r[i - 1];
			for (j = i - 2; t.r[j].key > t.r[0].key; j--) {
				t.r[j + 1] = t.r[j];
			}
			t.r[j + 1] = t.r[0];
		}
	}
}

//折半插入排序
void BInsertSort(SqList &t) {
	for (int i = 2; i <= t.length; i++) {
		int low, high, m;
		t.r[0] = t.r[i];
		low = 1;
		high = i - 1;
		while (low <= high) {
			m = (low + high) / 2;
			if (t.r[0].key < t.r[m].key)
				high = m - 1;
			else
				low = m + 1;
		}
		for (int j = i; j > high + 1; j--) {
			t.r[j] = t.r[j - 1];
		}
		t.r[high + 1] = t.r[0];
	}
}

//希爾排序
void ShellInsert(SqList &t, int dk) {
	for (int i = dk + 1; i <= t.length; i++) {
		if (t.r[i].key < t.r[i - dk].key) {
			int j;
			t.r[0] = t.r[i];
			t.r[i] = t.r[i - dk];
			for (j = i - 2 * dk; j > 0 && (t.r[j].key > t.r[0].key); j = j - dk)
				t.r[j + dk] = t.r[j];
			t.r[j + dk] = t.r[0];
		}
	}
}
void ShellSort(SqList &t) {
	int temp = t.length, i, j;
	int *const dt = (int *)malloc(sizeof(int) * t.length);
	for (i = 0; temp != 0; i++) {
		//增量序列參考某文章,對於length<10000時的較高效率
		temp = temp / 3;
		dt[i] = temp + 1;
	}
	for (int j = 0; j <= i - 1; j++)
		ShellInsert(t, dt[j]);
}

//冒泡排序
void BubbleSort(SqList &t) {
	int m, j, flag = 1;
	m = t.length - 1;
	while (m > 0 && flag) {
		flag = 0;
		for (j = 1; j <= m; j++) {
			if (t.r[j].key > t.r[j + 1].key) {
				flag = 1;
				t.r[0] = t.r[j];
				t.r[j] = t.r[j + 1];
				t.r[j + 1] = t.r[0];
			}
		}
		m--;
	}
}

//快速排序
void QuickSort(SqList &t, int low, int high) {
	if (low < high) {
		int left = low, right = high;
		t.r[0] = t.r[low];
		while (low < high) {
			while (low < high && t.r[high].key >= t.r[0].key)
				high--;
			t.r[low] = t.r[high];
			while (low < high && t.r[low].key <= t.r[0].key)
				low++;
			t.r[high] = t.r[low];
		}
		t.r[low] = t.r[0];
		QuickSort(t, left, low - 1);
		QuickSort(t, low + 1, right);
	}
}
//簡單選擇排序
void SelectSort(SqList &t) {
	int min;
	for (int i = 1; i < t.length; i++) {
		min = i;
		for (int j = i + 1; j <= t.length; j++) {
			if (t.r[j].key < t.r[min].key)
				min = j;
		}
		if (min != i) {
			t.r[0] = t.r[min];
			t.r[min] = t.r[i];
			t.r[i] = t.r[0];
		}
	}
}
//篩選堆
void HeapAdjust(SqList &t, int s, int m) {
	t.r[0] = t.r[s];
	for (int i = 2 * s; i <= m; i *= 2) {
		if (i < m && t.r[i].key < t.r[i + 1].key)
			i++;
		if (t.r[0].key >= t.r[i].key)
			break;
		t.r[s] = t.r[i];
		s = i;
	}
	t.r[s] = t.r[0];
}
//創建堆
void CreateHeap(SqList &t) {
	int n = t.length;
	for (int i = n / 2; i >= 1; i--) {
		HeapAdjust(t, i, n);
	}
}
//堆排序
void HeapSort(SqList &t) {
	CreateHeap(t);
	for (int i = t.length; i >= 2; i--) {
		t.r[0] = t.r[1];
		t.r[1] = t.r[i];
		t.r[i] = t.r[0];
		HeapAdjust(t, 1, i - 1);
	}
}
//歸併
void Merge(SqList &t, RedType *&S, int low, int high) {
	int i = low, k = low, mid = (low + high) / 2;
	int j = mid + 1;
	while (i <= mid && j <= high) {
		if (t.r[i].key <= t.r[j].key)
			S[k++] = t.r[i++];
		else
			S[k++] = t.r[j++];
	}
	while (i <= mid)
		S[k++] = t.r[i++];
	while (j <= high)
		S[k++] = t.r[j++];
	for (int m = low; m <= high; m++)
		t.r[m] = S[m];
}
//歸併排序
void MergeSort(SqList &t, RedType *&S, int low, int high) {
	if (low >= high) {
		S[low] = t.r[low];
	} else {
		int mid = (low + high) / 2;
		MergeSort(t, S, low, mid);
		MergeSort(t, S, mid + 1, high);
		Merge(t, S, low, high);
	}
}

void menu() {
 	cout << endl;
	cout << "    ----排序操作----    " << endl;
	cout << "************************" << endl;
	cout << "*   1---產生隨機數     *" << endl;
	cout << "*   2---直接插入排序   *" << endl;
	cout << "*   3---折半插入排序   *" << endl;
	cout << "*   4---希爾排序       *" << endl;
	cout << "*   5---冒泡排序       *" << endl;
	cout << "*   6---快速排序       *" << endl;
	cout << "*   7---簡單選擇排序   *" << endl;
	cout << "*   8---堆排序         *" << endl;
	cout << "*   9---歸併排序       *" << endl;
	cout << "*   0---退出           *" << endl;
 	cout << "************************" << endl;
	cout << "請選擇菜單(0-9):";
}

int List() {
	int n = -1, flag = 0;
	SqList T, R;
	RedType *S = (RedType *)malloc(sizeof(RedType) * T.length + 1);
	while (n != 0) {
		menu();
		cin >> n;
		switch (n) {
			case 1:
				cout << "產生隨機數如下" ;
				producerandom(T);
				flag = 1;
				break;
			case 2:
				if (flag) {
					cout << "直接插入排序" ;
					R = T;
					InsertSort(R);
					print(R);
				} else {
					cout << "請先產生隨機數" << endl;
				}
				break;
			case 3:
				if (flag) {
					cout << "折半插入排序" ;
					R = T;
					BInsertSort(R);
					print(R);
				} else {
					cout << "請先產生隨機數" << endl;
				}
				break;
			case 4:
				if (flag) {
					cout << "希爾排序" ;
					R = T;
					ShellSort(R);
					print(R);
				} else {
					cout << "請先產生隨機數" << endl;
				}
				break;
			case 5:
				if (flag) {
					cout << "冒泡排序";
					R = T;
					BubbleSort(R);
					print(R);
				} else {
					cout << "請先產生隨機數" << endl;
				}
				break;
			case 6:
				if (flag) {
					cout << "快速排序";
					R = T;
					QuickSort(R, 1, R.length);
					print(R);
				} else {
					cout << "請先產生隨機數" << endl;
				}
				break;
			case 7:
				if (flag) {
					cout << "簡單選擇排序" ;
					R = T;
					SelectSort(R);
					print(R);
				} else {
					cout << "請先產生隨機數" << endl;
				}
				break;
			case 8:
				if (flag) {
					cout << "堆排序" ;
					R = T;
					HeapSort(R);
					print(R);
				} else {
					cout << "請先產生隨機數" << endl;
				}
				break;
			case 9:
				if (flag) {
					cout << "歸併排序" ;
					R = T;
					MergeSort(R, S, 1, R.length);
					print(R);
				} else {
					cout << "請先產生隨機數" << endl;
				}
				break;
			case 0:
				cout << "退出成功" << endl;
				break;
			default:
				cout << "輸入數字錯誤,請重新輸入" << endl;
				break;
		}
	}
	return 0;
}

int main() {
	List();
	return 0;
}

作者文壇寫於2020年6月6日

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章