在另一篇中级篇我提到了堆排序它的时间复杂度为O(nlogn),我现在要回顾的也是另一个时间复杂度为O(nlogn)的排序算法-归并排序,实现的时候我采用的二分递归调用,算法的关键是如何对两个已经有序的序列进行归并。其实很简单,遍历两个有序的序列,把小的(或大的)插入临时数组中,一直做这样的操作直到遍历完两个序列。
实现代码如下:
/* FileName: MergeSort.cpp Author: ACb0y Create Time: 2011年2月15日14:49:47 Last modify Time: 2011年2月15日15:55:58 */ #include <iostream> using namespace std; /* 函数名: template <class type> void print(type * data, int n, char * format); 功能:输出元素序列中所有的元素 参数: 输入: data (type *): 元素序列的头指针 n (int): 元素序列中元素的个数 format (char*): 元素输出格式 输出:无 返回值: 无 */ template <class type> void print(type * data, int n, char * format) { for (int i = 0; i < n; ++i) { printf(format, data[i]); } printf("/n"); } /* 函数名: template <class type> void merge( type * data, int down, int mid, int up, bool cmp(const type & lv, const type & rv) ) 功能:对指定区域内的元素序列进行一次归并操作 参数: 输入: data (type *): 元素序列的头指针 down (int): 归并区域下边界 mid (int): 归并区域中界 up (int): 归并区域上边界 cmp (bool (const type &, const type &): 输出:无 返回值:无 */ template <class type> void merge( type * data, int down, int mid, int up, bool cmp(const type & lv, const type & rv) ) { type * pTmp = new type[up - down + 1]; int c = 0; int i = down; int j = mid + 1; while (i <= mid && j <= up) { if (cmp(data[i], data[j])) { pTmp[c++] = data[i]; ++i; } else { pTmp[c++] = data[j]; ++j; } } while (i <= mid) { pTmp[c++] = data[i++]; } while (j <= up) { pTmp[c++] = data[j++]; } memcpy(data + down, pTmp, sizeof(type) * (up - down + 1)); delete [] pTmp; } /* 函数名: template <class type> void mergeSort(type * data, int down, int up, bool cmp(const type & lv, const type & rv)); 功能:二分归并排序(采用递归算法) 参数: 输入: data (type *): 元素序列的头指针 down (int): 排序元素序列的下边界 up (int): 排序序列的上边界 cmp (bool (const type &, const type &)): 元素比较函数谓词 输出:无 返回值:无 */ template <class type> void mergeSort(type * data, int down, int up, bool cmp(const type & lv, const type & rv)) { if (down < up) { int mid = (down + up) >> 1; mergeSort(data, down, mid, cmp); mergeSort(data, mid + 1, up, cmp); merge(data, down, mid, up, cmp); } } /* 函数名:bool com_int(const int & lv, const int & rv); 功能:整型元素比较谓词 参数: 输入: lv (const int &): 左值 rv (const int &): 右值 输出:无 返回值: true: lv < rv false: lv >= rv */ bool cmp_int(const int & lv, const int & rv) { if (lv < rv) { return true; } return false; } int main() { int data[12] = {1, 30, 40, 4, 7, 234, 2, 3, 342, 2, 7546, 15}; mergeSort(data, 0, 11, cmp_int); print(data, 12, "%d "); return 0; }
运行结果: