插入排序
算法思想
每次将一个待排序的记录按其关键字大小插入到前面已排好序的子序列中,直到全部记录插入完成
动图展示:
排序(冒泡排序,选择排序,插入排序,归并排序,快速排序,计数排序,基数排序) - VisuAlgo
代码实现
简单直接插入排序
/**
* 插入排序
* @param nums 待排序数组
* @param len 数组的长度
*/void insertSort(int *nums, int len) {
int j, i;
for (i = 1; i < len; ++i) {
if (nums[i] < nums[i - 1]) {
int temp = nums[i];
for (j = i - 1; j > 0 && temp < nums[j]; --j) {
nums[j + 1] = nums[j];
}
nums[j + 1] = temp;
}
}
}
折半插入排序
在观看本段内容时,需要 二分查找法 相结合,折半查找关键代码如下
int low = 0;
int high = list->length;
int mid = 0;
//二分查找
while (low <= high) {
mid = (low + high) / 2;//这里可以使用位移
// mid = (low + high) >> 1;
if (list->data[mid] == target) {
break;
}
if (list->data[mid] > target) {
high = mid - 1;
} else {
low = mid + 1;
}
}
折半插入排序代码如下:
void midInsertSort(int *nums, int len) {
int i, j, temp, low, high, mid;
for (i = 1; i < len; ++i) {
temp = nums[i];
low = 1, high = i;
while (low <= high) {
mid = (low + high) >> 2;
if (nums[mid] > temp) {
high = mid - 1;
} else {
//mid指向当前元素也需要low后移一位,保证算法的稳定性
low = mid + 1;
}
}
//开始右移,从low开始位移,low为大于temp的第一位数
for (j = low; j < i; ++j) {
nums[j + 1] = nums[j];
}
nums[low] = temp;
}
}
拓展:带哨兵的插入排序
原理其实大同小异,这里就不过分说明。