几种常见排序算法
public static void Run() { const int arrayCount = 10000; const int arraySize = 400; var arrList = new List<int[]>(arrayCount); var arrList1 = new List<int[]>(arrayCount); var arrList2 = new List<int[]>(arrayCount); var arrList3 = new List<int[]>(arrayCount); var watch = new Stopwatch(); watch.Start(); for (var i = 0; i < arrayCount; i++) { var rd = new Random(); var arr = new int[arraySize]; for (var j = 0; j < arraySize; j++) { arr[j] = rd.Next(arraySize); } arrList.Add(arr); arrList1.Add((int[])arr.Clone()); arrList2.Add((int[])arr.Clone()); arrList3.Add((int[])arr.Clone()); } watch.Stop(); Console.WriteLine($"生成测试数据,耗时:{watch.ElapsedMilliseconds}ms"); watch.Restart(); foreach (var arr in arrList) { Sample01.BubbleSort(arr); } watch.Stop(); Console.WriteLine($"冒泡排序,耗时:{watch.ElapsedMilliseconds}ms"); watch.Restart(); foreach (var arr in arrList1) { Sample02.InsertSort(arr); } watch.Stop(); Console.WriteLine($"插入排序,耗时:{watch.ElapsedMilliseconds}ms"); watch.Restart(); foreach (var arr in arrList2) { Sample04.MergeSort(arr); } watch.Stop(); Console.WriteLine($"归并排序,耗时:{watch.ElapsedMilliseconds}ms"); watch.Restart(); foreach (var arr in arrList3) { Sample05.QuickSort(arr); } watch.Stop(); Console.WriteLine($"快速排序,耗时:{watch.ElapsedMilliseconds}ms"); }
1.BubbleSort
public static void BubbleSort(int[] a) { if (a.Length <= 1) return; for (var i = 0; i < a.Length; ++i) { var flag = false; for (var j = 0; j < a.Length - i - 1; j++) { if (a[j] <= a[j + 1]) continue; // 逆序度是K*3 var tmp = a[j]; a[j] = a[j+1]; a[j+1] = tmp; flag = true; } if (!flag) break; } }
2.InsertSort
public static void InsertSort(int[] a) { if (a.Length <= 1) return; for (var i = 1; i < a.Length; i++) { var value = a[i]; var j = i - 1; // 查找插入的位置 for (; j >= 0; j--) { // 比较 if (a[j] > value) { // 移动数据 // K! a[j+1] = a[j]; } else { break; } } // 插入 a[j+1] = value; } }
3.MergeSort
public static void MergeSort(int[] a) { MergeSort(a, 0, a.Length - 1); } public static void MergeSort(int[] a, int m, int n) { //递归终止条件 if(m>=n) return; // 取m到n之间的中间位置 x var x = (m + n) / 2; // 分治递归 MergeSort(a, m, x); MergeSort(a, x + 1, n); Merge(a, m, x, n); } public static void Merge(int[] a, int m, int x, int n) { var i = m; var j = x+1; var k = 0; // 申请一个大小和a[m...n]一样的临时数组 var tmp = new int[n - m + 1]; // 比较 while (i<=x && j<=n) { if (a[i] <= a[j]) { tmp[k] = a[i]; k++; i++; } else { tmp[k] = a[j]; k++; j++; } } // 判断哪个子数组有剩余的数据 var start = i; var end = x; if (j <= n) { start = j; end = n; } // 将剩余的数据拷贝到临时数组tmp while (start <= end) { tmp[k] = a[start]; k++; start++; } // 将tmp中的数组拷贝回 for (i = 0; i <= n-m; i++) { a[m+i] = tmp[i]; } }
4.QuickSort
public static void QuickSort(int[] a) { QuickSort(a, 0, a.Length - 1); } public static void QuickSort(int[] a, int m, int n) { if (m >= n) return; // 获取分区点 var x = Partition(a, m, n); QuickSort(a, m, x-1); QuickSort(a, x+1, n); } public static int Partition(int[] a, int m, int n) { var pivot = a[n]; var i = m; int tmp; for(var j = m; j < n; j++) { if (a[j] >= pivot) continue; if (i == j) { i++; } else { tmp = a[i]; a[i] = a[j]; a[j] = tmp; i++; } } tmp = a[i]; a[i] = a[n]; a[n] = tmp; return i; }