持续创作,加速成长!这是我参与「掘金日新计划 · 10 月更文挑战」的第30天,点击查看活动详情
1、快速排序
快速排序采用的是分治的思想,他的时间复杂度是nlogn。 首先第一步我们要在数组找一个基数,可以是第一个数,也可以是最后一个数,或者是中间位置的数,甚至是数组中任意一个数。
第二步是把真个数组以及数为准分为大于基数的右半部分和小于基数的左半部分。
第三步是采用递归的方法对左右两半部分重复步骤一与步骤二。
void Q_sort(int arr[], int L, int R)
{//参数列表:arr数组名 L左边界 R右边界
if (L >= R) return;//如果数组的长度为0或1就不排序。
int jishu = arr[L], i = L - 1, j = R + 1, temp;
//i,j是两个指针;
//i指向数组左端,向右移动;
//j指向数组有端,向左移动;
while (i<j)
{
do i++; while (arr[i] < jishu);
//如果小于基数就现在左移动,我们要找大于等于基数的
do j--; while (arr[j] > jishu);
//如果大于基数就现在左移动,我们要找小于等于基数的
if (i < j)
//两边都找到之后进行交换各取所需
{
temp = arr[i];
arr[i] = arr[j];
arr[j] = temp;
}
}
//然后递归对量两边分治进行排序
Q_sort(arr, L, j);//i,j反映的都是下标,小于等于j的都是
Q_sort(arr, j + 1, R);
}
2、归并排序
合并排序的时间复杂度也是nlogn。 我的理解是他把一个数组自上向下等分,知道成对的两部分都是有序的(基本都是一个数成一个子数组了),然后再子下而上的开始和合并。
int temp[100000];
void m_sort(int arr[], int L, int R)
{
if (L >= R) return 0;
int mid = (L + R) >> 1;//除以二
m_sort(arr, L, mid), m_sort(arr, mid + 1, R);//极限分割
//递归排序左右两边,俩边都有序了在合并。
int k = 0, i = L, j = mid + 1;//一半一半
//合并给到一个临时数组
while (i<=mid&&j<=R)//
{
if (arr[i] <= arr[j]) temp[k++] = arr[i++];
else temp[k++] = arr[j++];
}
//剩余直接加进去
while (i <= mid) temp[k++] = arr[i++];
while (j <= R) temp[k++] = arr[j++];
//copy,吧临时数组的内容在赋值给arr
for (i = L, j = 0; i <= R; i++, j++) {
arr[i] = temp[j];
}
}