1. 堆排序
/* * 手动实现堆排序, 使用大根堆实现 从小到大排序 */ // 完成在数组[low, high]的范围内,对在位置low上的节点向下进行调整 void shift(int nums[], int low, int high) { int i = low; int j = i*2; int tmp = nums[i]; while(j<=high) { // 比较当前节点的左、右儿子 if(j<high && nums[j]<nums[j+1]) j++; //如果右儿子较大则让j指向较大的儿子节点的下标 if(tmp < nums[j]) { nums[i] = nums[j]; i = j; j = i*2; } else break; } nums[i] = tmp; } void heap_sort(int nums[], int n) { int tmp; // 建立初始化的堆, 从第一个非叶子结点进行调整 for(int i=n/2; i>=1; i--) { shift(nums, i, n); } // 进行n-1次循环, 完成堆排序, 把堆顶元素放到后面 for(int i=n; i>=2; i--) { tmp = nums[1]; nums[1] = nums[i]; nums[i] = tmp; shift(nums, 1, i-1); } } int main() { int n; scanf("%d", &n); int nums[100]; // 读入n个数据, 堆一棵完全二叉树,必须从1开始存储 for(int i=1; i<=n; i++) { scanf("%d", &nums[i]); } // 进行堆排序 heap_sort(nums, n); // 打印排序后的数组 for(int i=1; i<=n; i++) { printf("%d ", nums[i]); } return 0; }
2. 归并排序
/* * 实现二路归并排序 */
// 合并函数:原数组、辅助数组、开始下标,中间下标、结束下标 void Merge(int sourceArray[], int tempArray[], int s, int mid, int t) { int i = s; int j = mid+1; int k = s; while(i<=mid && j<=t) { if(sourceArray[i] <= sourceArray[j]) tempArray[k++] = sourceArray[i++]; else tempArray[k++] = sourceArray[j++]; } while(i<=mid) tempArray[k++] = sourceArray[i++]; while(j<=t) tempArray[k++] = sourceArray[j++]; for(i=s; i<=t; i++) sourceArray[i] = tempArray[i]; } // 原数组,辅助数组,开始下标,结束下标 void MergeSort(int sourceArray[],int tempArray[],int s,int t) { if(s<t) { int mid = (s+t)>>1; // 递归排序左边 MergeSort(sourceArray,tempArray,s,mid); // 递归排序右边 MergeSort(sourceArray,tempArray,mid+1,t); // 合并 Merge(sourceArray,tempArray,s,mid,t); } }