归并排序
归并,就是把元素合并在一起,在这里我们主要是通过把数据元素分开,当数组元素细化后将它在合并起来。
在归并算法中,主要用到了分治和合并的两种思想。分治:将数组元素细化,分成n多个单个元素序列。合并:一步一步将分治的数组元素合并起来,合并的同时进行顺序排序。
//归并排序
void Merge(int TR2[], int TR1[], int i, int m, int n)
{
// 合并两个数组
int j, k, l;
for (j = m + 1, k = i; i <= m && j <= n; k++)
{
if (TR2[i] < TR2[j])
TR1[k] = TR2[i++];
else
TR1[k] = TR2[j++];
}
if (i <= m)
{
for (l = 0; l <= m - i; l++)
TR1[k + l] = TR2[i + l];
}
if (j <= n)
{
for (l = 0; l <= n - j; l++)
TR1[k + l] = TR2[j + l];
}
}
void MSort(int SR[], int TR1[], int num, int Array_length)
{
// 分治实现
int merger_len; // 设置临时变量,记录每次归并的长度
int TR2[MAX_SIZE + 1]; // 用来合并分治的元素,进行重新排列
if (num == Array_length) {
// 当分治的每个序列只有一个元素,则停止分治,否则继续分治
TR1[num] = SR[num];
}
else {
merger_len = (num + Array_length) / 2;
// 进行递归方法实现每层分治
MSort(SR, TR2, num, merger_len); // 对分治后的前merger_len进行递归分治
MSort(SR, TR2, merger_len + 1, Array_length); // 对分治后的merger_len后的元素进行递归分治
Merge(TR2, TR1, num, merger_len, Array_length); // 对分治部分进行合并
}
}
void MergeSort(SqList* L) // 归并排序主函数
{
MSort(L->Array, L->Array, 1, L->length);
}
对于具体的过程分析我们用图来展示:
我们把分治过程和合并过程分开展示(实际过程分治和合并时同时进行的)
对于分治递归中的红色框图是第一部,紧接着进行合并,随后在惊醒蓝色框图中的分治,接着进行合并,依据这样的方式不断将原数组进行分治合并,便可得到有序的数组序列。
以上是鄙人对该算法的理解,若与实际算法思想有出入,还请多多指教。