排序算法稳定性:在原序列中,ri=rj,且ri在rj之前,而在排序后的序列中,ri仍在rj之前,则称这种排序算法是稳定的;否则称为不稳定的。
#include <stdio.h> #include <stdlib.h> /* EazyChange 2016.06.12 Sort C language */ /* 插入排序 思想:从第i个元素开始,前移到i+1中正确的位置上,前i个元素默认有序 最好情况n,最坏情况n2,稳定 */ void InsertionSort_wrong(int data[], int n) { int i = 0, j = 0; for (i = 1; i < n; i++) { int tmp = data[i];//记录当前值 for (j = i; j > 0; j--)//从当前值开始向前遍历 { if (data[j-1] > tmp)//记住,这样写是错的!增加了时间复杂度 { data[j] = data[j-1]; data[j-1] = tmp; } } } } void InsertionSort(int data[], int n) { int i = 0, j = 0; for (i = 1; i < n; i++) { int tmp = data[i]; for (j = i; j>0 && data[j - 1] > tmp; j--)//这步保证最好情况时间复杂度为n { data[j] = data[j-1]; } data[j] = tmp;//这步注释碉堡了!为什么是j呢?因为循环找到了一个j-1《tmp,所以tmp在j-1后面 } } /* 选择排序 思想:每一次从待排序的数据元素中选出最小的一个元素,存放在序列的起始位置 最好情况n2,最坏情况n2,不稳定 */ void SelectSort(int data[], int n) { int i = 0, j = 0; int min_index = 0;//最小元素下表 int min_num = 0;//最小元素值 for (i = 0; i < n; i++) {
min_index = i;//20160613加入,很重要,因为如果下面的条件没有判断,则min_index类似“野指针”一样,不过还停留在上面那个数,所以会有重复的数出现 min_num = data[i]; for (j = i+1 ; j < n; j++)//循环为找到最小元素 { if (data[j] < min_num) { min_num = data[j]; min_index = j;//并记录下标 } } data[min_index] = data[i];//与第一个元素替换 data[i] = min_num; } } /* 冒泡排序 思想:通过从开始遍历逐渐把最大的数放大末尾 最好情况n2,最坏情况n2,不稳定,因为有>= */ void BubbleSort(int data[], int n) { int i = 0, j = 0; for (i = 0; i < n - 1; i++) { for (j = 0; j < n - 1 - i; j++) { if (data[j] >= data[j + 1]) { int tmp = data[j]; data[j] = data[j + 1]; data[j + 1] = tmp; } } } } /* 快速排序 思想:右边找一个数放左边,左边找一个数放右边,最后赋中间值,产生一个中间值序列。再递归。 最好情况nlogn,最坏情况n2,不稳定 */ void QuickSort(int data[], int left, int right) { if (left < right) { int i = left, j = right; int tmp = data[left]; while (i < j)//这一趟排序产生一个中间数的序列 { while (i < j && data[j]>tmp)//从右边找到第一个小于tmp的数 { j--; } if (i < j)//把那个数给第左边计数值 { data[i++] = data[j]; } while (i < j && data[i] < tmp)//从左边找到第一个大于tmp的数 { i++; } if (i < j)//把那个数给右边计数值 { data[j--] = data[i]; } } data[i] = tmp;//再把中间值赋给何时的位置 /* for (int k = 0; k < 11; k++) { printf("%d ", data[k]); } printf(" ");*/ QuickSort(data, left, i - 1);//此时中间值在i的位置,从left到i-1再来一遍 QuickSort(data, i + 1, right);//从i+1到right再来一遍 } } int main(void) { int mat[] = { 3, 2, 1, 4, 6, 15, 8, 9, 10, 13, 21 }; //BubbleSort(mat, sizeof(mat) / sizeof(mat[0])); QuickSort(mat, 0, 10); return 0; }
附上一个快速排序时间复杂度分析:http://book.51cto.com/art/201108/287089.htm