算法之合并排序(mergeSort)

  合并排序算法在结构上是递归的,采用分治策略:就是将原有的问题划分为 n 个规模较小但结构与原问题相似的子问题,递归地解决这些子问题,然后合并其结果,就得到原问题的解。

  合并排序的模式一般如下:

  1.分解:将 n 个元素分解为各含 n/2 个元素的两个序列;

  2.解决:用分治排序法对两个子序列递归地排序;

  3.合并:合并两个已排好序的子序列得到排序结果。

  在对子序列递归的过程中,当子序列元素数为1时,递归结束。

  合并排序算法的时间复杂度为O(nlgn)

 1 void merge(int* a, int p, int q, int r)
 2 {
 3     int i = 0;
 4     int j = 0;
 5     int k = 0;
 6     int n1 = q - p + 1;
 7     int n2 = r - q;
 8     int* L = (int*)malloc((n1 + 1) * sizeof(int));
 9     int* R = (int*)malloc((n2 + 1) * sizeof(int));
10     for(i = 0; i < n1; i++)
11     {
12         *(L + i) = a[p + i];
13     }
14     *(L + n1) = INT_MAX;    //插入序列末标志
15
16     for(i = 0; i < n2; i++)
17     {
18         *(R + i) = a[q + i + 1];
19     }
20     *(R + n2) = INT_MAX;    //插入序列末标志
21
22     i = 0;
23     j = 0;
24     k = 0;
25     for(k = p; k < r + 1 ;k++)
26     {
27         if(*(L + i) > *(R + j))
28         {
29             *(a + k) = *(R + j);
30             j++;
31         }
32         else
33         {
34             *(a + k) = *(L + i);
35             i++;
36         }
37     }
38 }
39
40 void mergeSort(int* a, int p, int r)
41 {
42     int q = 0;
43     if(p < r)
44     {
45         q = (r + p) / 2;
46         mergeSort(a, p, q);
47         mergeSort(a, q + 1, r);
48         merge(a, p, q, r);
49     }
50 }

注:1. mergeSort(int* a, int p, int r) 和 merge(int* a, int p, int q, int r)中的形参 p, q, r 都是序列 a 的索引,其中子序列 L = (a[p] ~ a[q]),其长度为 q - p + 1;子序列 R = (a[q + 1] ~ a[r]),其长度为 r - (q + 1) - 1 即 r - q;

   2.在上述代码中都插入了 序列标志数,这个数默认为∞,但在实际应用中,该数有可能会出现在应用序列中,merge函数可改为如下:

 1 void merge(int* array, int p, int q, int r)
 2 {
 3     int i = 0;
 4     int j = 0;
 5     int k = 0;
 6     int n1 = q - p + 1;
 7     int n2 = r - q;
 8     int* L = (int*)malloc((n1) * sizeof(int));
 9     int* R = (int*)malloc((n2) * sizeof(int));
10     for(i = 0; i < n1; i++)
11     {
12         *(L + i) = array[p + i];
13     }
14     //*(L + n1) = INT_MAX;
15
16     for(j = 0; j < n2; j++)
17     {
18         *(R + j) = array[q + j + 1];
19     }
20     //*(R + n2) = INT_MAX;
21
22     i = 0;
23     j = 0;
24     k = 0;
25     for(k = p; k < r + 1 ;k++)
26     {
27         if(i > (n1 - 1))
28         {
29             *(array + k) = *(R + j);
30             j++;
31         }
32         else if(j > (n2 - 1))
33         {
34             *(array + k) = *(L + i);
35             i++;
36         }
37         else
38         {
39             if(*(L + i) > *(R + j))
40             {
41                 *(array + k) = *(R + j);
42                 j++;
43             }
44             else
45             {
46                 *(array + k) = *(L + i);
47                 i++;
48             }
49         }
50     }
51 }
时间: 2024-10-07 04:49:10

算法之合并排序(mergeSort)的相关文章

第二章 算法入门 合并排序

在第二章中难的算法不多,接下来我会把稍微复杂一点的算法整理一下 #include <iostream> using namespace std; void mergeSort(int *A,int left,int mid,int right) { int *L=new int[mid-left+1]; int *R=new int[right-mid+1]; int i,j; for(i=0;i<mid-left+1;i++) { L[i]=A[left+i]; } for (j=0;

算法之合并排序

上篇文章讲到插入排序算法,是一个标准的增量方法:在排好的子数组后,将元素插入,形成新的数组.今天要介绍的是一种新方法:分治法. 分治法,将原问题划分成n个规模较小而结构与原问题相似的子问题:递归地解决这些子问题,然后再合并其结果,就能得到原问题的解.在每一层递归上都会有三个步骤: 分解:将原问题分解成一系列子问题: 解决:递归地解决各子问题,若子问题足够小,则直接求解: 合并:将子问题的结果合并成原问题的解. 合并排序算法完全依照了上述模式,直观的操作如下: 分解:将n个元素分成各含n/2个元素

【算法】合并排序

#include <STDIO.H> #include <STDLIB.H> void mergePass(int *ar,int *pr,int s,int size); void merge(int *ar,int *pr,int l,int m,int r); void mergeSort(int *ar,int size) // 合并排序 { int *pr=(int *)malloc(sizeof(int)*size); //动态开辟要排序数组大小的一个新数组 int s

Python实现合并排序MergeSort

def merge(sort_list, start, mid, end): left_list = sort_list[start:mid] right_list = sort_list[mid:end] left_list.append(float("inf")) right_list.append(float("inf")) left_index = right_index = 0 i = start while i < end: if left_lis

算法实验:分治法合并排序(C++)

这篇文章分两部分来写,第一部分写代码的实现过程,第二部分把实验报告从头到尾呈现出来. 我习惯调试使用的编译器是DEV C++,不是vs系列的,可能头文件上有点区别.但是下面的报告是我放到vs里面测试过的,可以直接用,不影响. 第一部分:(解析) 题目:随机产生一个整型数组,然后用合并排序将该数组做升序排列,要求输出排序前和排序后的数组. 题目分析: 需要随机产生一个整数数组: 采用的算法是合并排序,也就是用归并排序: 输出排序后的数组. 随机产生一个整数数组:这个问题首先想到的是用rand()函

分治——合并排序

分治策略中有一个经典的算法就是合并排序,这个算法的精髓也是分治二字,分而治之.将一个大规模的问题分割成若干个同样的小问题,小问题的规模很小,很容易解决,解决了小的问题后再对这些小问题的结果进行合并得到大规模问题的解答. 合并排序便是分治策略中比较经典的算法,首先是合并,两个排列有序的数列经过合并后成为有序的数组:代码如下: void _merge(int *A,int left,int middle,int right) { int i=left,j=middle+1,k=0; int *C;

【合并排序法】

/* 合并排序法 */ #include <stdio.h> #include <stdlib.h> #include <time.h> #define MAX1 10 #define MAX2 10 #define SWAP(x,y) {int t; t = x; x = y; y = t;} int partition(int[], int, int); void quicksort(int[], int, int); void mergesort(int[], i

分治算法——合并排序与自然排序

合并排序算法: public class MergeSort { public static void MergeSort(int A[],int low,int high){ if(low<high){ int middle=(low+high)/2; MergeSort(A,low,middle); MergeSort(A,middle+1,high); Merge(A,low,middle,high); } } public static void Merge(int A[],int lo

让我们来谈谈合并排序算法

转载请注明出处:http://blog.csdn.net/ruoyunliufeng/article/details/27570953 归并操作(merge),也叫归并算法,指的是将两个已经排序的序列合并成一个序列的操作.归并排序算法依赖归并操作. 一.归并排序算法 /*************************************************************** *版权全部 (C)2014,公司名称. * *文件名:归并排序法 *内容摘要:无 *其他说明:无 *当