美文网首页
四种算法思想(上)- 分治、回溯

四种算法思想(上)- 分治、回溯

作者: Wu杰语 | 来源:发表于2019-06-02 15:15 被阅读0次

四种算法思想

学习算法,有两个比较重要的基础要学习。

  • 首先是复杂度的计算。复杂度包括时间复杂度和空间复杂度,通过对一个问题的不同算法,通过比较时间复杂度和空间复杂度,我们选择针对这个问题最合适的算法。就像架构师选择架构所做的事情一样。
  • 其次是算法思想。目前的算法书籍总结了四种基本的算法思想,用以指导算法的开发,分别是分治、回溯、贪婪和动态规划。

对于四种算法思想,我们学习后当然需要能讲得清并且反复练习直至掌握,这四种算法思想的掌握还是非常有难度的,特别是动态规划。

理解四种算法思想

四种算法要理解并学习实在不易,学习就是为了用,那么怎么学比较好呢,学习原理,记忆模版。学习原理是为了真正理解,记忆模版是为了如何用,因为真的抽象度高,通过模版能够降低使用的门槛难度。光学不用就会出现学了忘忘了学的死循环,光用不学就发现不会用,只会学过的问题。

分治

分治最典型就是mergySort了,这个排序算法是在学习排序的时候必学的,用到就是分治思想。

什么样的问题适合用分治思想解决?那么就是如下几点:

  • 一个大问题可以拆解程若干小问题。
  • 每个小问题可以再拆解或者到达终止条件。例如说mergy算法,最终拆解到只剩一个元素,到达了终止条件。
  • 每个小问题各不相同,如果小问题都相同。
  • 小问题处理完后能合并回原来的整体。
    为什么要强调如上几个点,就是为了和动态规划、回溯、贪婪算法区分开来。这几种算法的特点等会在下面说。一个明显的不同就是后者存在相同的子问题,可以将相同的子问题缓存下来,避免多次计算。

最后咱们用的时候,就需要记忆一个模版,使用Python表达:

def divide_and_conquer(datas, paras):
    if exit_condition(datas): #终止条件
        return
    subData = split_data(datas)  #问题可被分解为不同的子问题
    result1 = divide_and_conquer(subdata[0], paras)
    result2 = divide_and_conquer(subdata[1], paras)
    result3 = divide_and_conquer(subdata[2], paras)
    ...
    result = mergy_data(result1, result2. result3...) #问题的结果可被还原为整体
    return result

回溯

回溯是一种暴力算法,如果需要用到遍历,那么就使用回溯。例如说alphago围棋,最简单容易想到的就是回溯暴力计算了,为了推测下一步走那个子胜率高,我们对于可能下的位置的点用回溯遍历计算出一个概率,然后选择胜率最高的位置放下一个子。但是对于围棋,需要超出人类想象的计算能力和存储能力才能用暴力计算完成,所以说需要用不同的算法优化等。

上述对于alphago的回溯计算也就说明了回溯算法的优缺点:

  • 优点是容易想到
  • 缺点是只能面对小数据集,使用面有限。

进而下一步的,如果想用回溯算法,需要进行优化。例如说在树和图的深度优先的回溯中,有个比较专门的优化名词,剪枝,也就是将一些不需要的路径给剪掉,从而减少计算量。

上模版:

def backtracking(level, paras):
    if exist_condition(level):
        return
    state = keepsate(level)  #保存当前状态
    backtracking(level+1, paras):
    reverseState(level, state) #恢复当前状态

小结

分治和回溯相对来说,是两种比较好掌握的算法思想,需要做的就是搞明白后,牢记模版,多多练习一下。

题外话:递归和迭代

如上模版中使用了递归的技巧,而在计算设计中SICP中讲解了为了提升效率迭代的技巧。一般的问题能用递归解决也就同时能用迭代解决,这是两个必须要掌握的基本技巧。

  • 递归是计算机的思考方式,其数学基础就是数学归纳法,基于某个子问题已成立的基础上,去思考下一层的问题。计算机的递归思维思考起来是比较自然的,但是实际上它是基于栈的,如果你把它展开,就会发现栈不停再随规模增长而增长,直到超出人的思考界限和计算机栈的容量。因此对于一些可能的递归,有尾递归的优化避免栈爆炸。
  • 迭代是另外一种技巧,讲中间结果作为状态保存起来传递,而避免使用栈。递归因为符合计算机思维,编码的时候简单,要想出并写出迭代却没有那么容易。

相关文章

  • 四种算法思想(上)- 分治、回溯

    四种算法思想 学习算法,有两个比较重要的基础要学习。 首先是复杂度的计算。复杂度包括时间复杂度和空间复杂度,通过对...

  • 那些经典算法:贪心算法

    贪心算法和分治算法、动态规划算法、回溯算法都是一种编程思想,深入理解这些编程思想,我们也可以根据实际情况设计自己的...

  • 一位算法工程师的自我修养

    数据结构与算法 基本算法思想动态规划贪心算法回溯算法分治算法枚举算法 算法基础 时间复杂度 空间复杂度 最大复杂度...

  • 常用几种算法

    贪心,分治,回溯,动态规划四种算法。 贪心算法 场景:我们有m个糖果和n个孩子,现在要把糖果分给这些孩子吃,但是糖...

  • 分治算法

    文章结构 如何理解分治算法 分治算法应用举例 1. 如何理解分治算法 1.1 分治算法的核心思想 分治算法的核心思...

  • 分治算法和回溯算法

    一、分治算法 核心思想就是分而治之,将原问题划分为n个规模较小的,并且结构与原问题相似的子问题,而后递归地解决这些...

  • Leetcode-Java(二十五)

    241. Different Ways to Add Parentheses 采用分治算法,分治算法的基本思想是将...

  • 互联网大厂常考算法及套路深度解析

    常考算法 暴力法 回溯法 分支限界法 分治法 动态规划 贪心法 暴力法 也称枚举法、穷举法、蛮力法。 基本思想: ...

  • 8.30 leetcode刷题(2)

    递归和回溯:17 电话号码 思路:运用递归去实现回溯算法的思想。回溯算法本质上是一种暴力搜索,通过递归调用去实现,...

  • 算法思想 - 分治算法

    其实相比于分治算法,我更愿意称之为分治“思想”。因为这种思想的应用非常广泛,不仅是在计算机中,在生活中到处都是分治...

网友评论

      本文标题:四种算法思想(上)- 分治、回溯

      本文链接:https://www.haomeiwen.com/subject/khpntctx.html