您的位置:首页 > 其它

排序算法-归并排序

2016-05-07 13:42 281 查看

将n个数分成n/2组,排序好,再两两合并,分成n/4组,再依次上去,因为已经排序好了,合并起来很快。

每次需要对比的次数为n次

比如n=64时

当n/4时,每队有4个数,总共有16组,第一队的4个数与第二队的4个数对比,需要最多8次。总共有8组(每组2对)需要对比,即对比64次,也就是n

即分解后都需要对比n次,那需要分解多少次呢?

64/2, 64/2/2, 64/2/2/2

就是需要分解log2^n次,64可以分解6次,2,4,8,16,32,64

所以归并排序的复杂度为O(nlgn),算法中log2#n(2为底)直接写成lgn即可,底数一般不考虑,因为n很大时,底数已经不是英雄数目的关键了

归并排序还有个好处,可以多线程分开执行,效率更高。

有点像平时打牌,左边一堆已经排好序的,右边已经排好序列,这两堆要排序,只需要依次比较他们最小的值,最多比较n次就结束了。好的情况,第一堆比较完了,第二堆很快与"空"比较。

int sort_merge(int* ptr_data, int start_index, int mid_index, int stop_index)

{

    int n1 = mid_index - start_index + 1; //

    int n2 = stop_index - mid_index;

    int* ptr_data1 = (int*)malloc(sizeof(int) * (n1 + 1));

    int* ptr_data2 = (int*)malloc(sizeof(int) * (n2 + 1));

    int i = 0;

    for(i = 0; i < n1; ++i)

    {

        ptr_data1[i] = ptr_data[i + start_index];

    }

    ptr_data1[n1] = 65535; // 设置一个最大的“空"值,这样ptr_data2对比起来肯定比它小

    for(i = 0; i < n2; ++i)

    {

        ptr_data2[i] = ptr_data[i + mid_index + 1];

    }

    ptr_data2[n2] = 65535;

    int data1_index = 0;

    int data2_index = 0;

    for(i = start_index; i < stop_index; ++i)

    {

        if (data1_index > n1 || data2_index > n2)

        {

            assert(0);

        }

        if (ptr_data1[data1_index] > ptr_data2[data2_index])

        {

             ptr_data[i] = ptr_data2[data2_index];

             ++data2_index;

        }

        else

     {

         ptr_data[i] = ptr_data1[data1_index];

            ++data1_index;

     }

    }

}
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: