Stanford Algorithm 1.5 - 1.7 记录

Merge Sort

该课程前面几节课作为入门, 所以会介绍一些算法, 但后面会有更扎实、底层诸如复杂度分析等内容.

按讲者说法, 这种算法还是比较实际引用广泛的, 我后来稍微google了一下, 说这种算法最坏最好情况都是一样的时间复杂度.

思想很简单, 属于Divide and Conquer , 就是递归的把它二分打散, 再用O(N)的函数把它们merge起来. 下面的代码是不去重的, 即有重复数字仍然包含在内.

def merge_sorted_lists(a, b):
    res = []
    # init indices for a, b
    i = 0
    j = 0
    while i < len(a) and j < len(b):
        if a[i] < b[j]:
            res.append(a[i])
            i = i + 1
        else:
            res.append(b[j])
            j = j + 1
    if i < len(a):
        res = res + a[i:]
    else:
        res = res + b[j:]
    return res

def merge_sort(l):
    # THIS IS for exit!!!
    if len(l) <= 1:
        return l
    a = l[:int(len(l)/2)]
    b = l[int(len(l)/2):]
    left = merge_sort(a)
    right = merge_sort(b)
    return merge_sorted_lists(left, right)
    
if __name__ == '__main__':
    l = [4,5,7,9,7,5,1,0,7,-2,3,-99,6]
    print(merge_sort(l))

在度量其复杂度时, 讲者采用的是recursive tree, 其实就是笨办法, 把递归过程全部列出来, 计算每一层级需要的代价. 在第j (j=0,1,2,...,logN)层, 有2^j子问题(就是需要merge的), 每个子问题的size是(至多)需要6(N/(2^j))的代价(代码行数). 因此, 不管在哪一层, 代价都是6N, 所以最多就是6N(1+logN).

最后编辑于
©著作权归作者所有,转载或内容合作请联系作者
平台声明:文章内容(如有图片或视频亦包括在内)由作者上传并发布,文章内容仅代表作者本人观点,简书系信息发布平台,仅提供信息存储服务。

推荐阅读更多精彩内容

  • Chapter 2 插入排序 线性查找 选择算法 归并排序算法 二分查找算法 冒泡排序 插入排序 循环不...
    只是无情绪阅读 5,371评论 0 1
  • 他是一名山上的酿酒翁,结庐而居,偶尔拎几壶上好的烧刀子下山,总有一个少年等着,同他坐在桥边垂竿而渔,一边喝酒,一边...
    夏梧桐阅读 2,454评论 1 0
  • public classMainActivityextendsAppCompatActivityimplement...
    烟雨冰封阅读 8,317评论 0 0
  • 《卖轮子》是一本幽默的故事书,同时又是一本打破旧思维的书,它没有去生硬的讲解营销是什么,而是通过一个卖轮子的故事,...
    陆小米101阅读 3,471评论 0 1
  • 我是个好孩纸
    Oncexagain阅读 1,391评论 0 0