本文为覃超算法训练营的课程笔记
以上都是顶尖职业选手区别于普通人的细节体现。
关于栈对于树的递归和迭代的作用 树的递归,可以在栈的帮助下将递归转换为迭代。
深度优先搜索 -> 栈广度优先搜索 -> 队列以下观点要牢记:
链表就是树,树就是图。分支就是动态规划,就是回溯,就是递归。化繁为简:先归纳(高中的数学归纳法),后演绎。所有的方法都只有一个方法。整个宇宙就是一个题
写程序只会用到三种语言。 a). if-else, switch -> branch b). for loop -> iteration c). recursion -> divide & conquer 以上3条,相当于几何世界中5大公理,从它们基础上推演出以下各种各样的算法:递归,搜索,动态规划,二分搜索,贪心,数学。(注意:在大脑中回忆每种算法的思路和解题代码模板)
面试中所谓的难题:都是来找重复性,且最后是来调用递归的。
分治可以有重复问题,也可以没有重复问题。如果有重复问题,最好缓存一下,那时候就变成动态规划了。分治和动态规划是有区别的,可以认为: 分治是一种暴力的动态规划。 动态规划是一种去重的分治,即每次在局部即取得最优解,淘汰次优解的的分治。
递归问题的两种解法 a). 记忆化搜索(LRU cache作为缓存) from functools import lru_cache @lru_cache(None) 对于别的语言,可以开一个map或者数组。如果不用lru-cache,也就是不用递归,那就要写循环递推了,即动态规划。 b). 动态规划 递归->动态规划,即为 从上到下的人脑思维模式 -> 计算机从下到上的递推模式。
一个好问题:某些问题人类的脑子都想不明白,还要人写出程序,这怎么可能?
我想给大家讲一点,这个在程序里是非常正常的,而且要训练一种思路。大家以后把算法掌握了,80%以上的面试题,以及解决业务上高难度的问题,都是那种用思维很难思考,但是你掌握好它里面的套路,或者它的重复性,用程序非常好的解决。希望大家一定要掌握这种思维。 为什么?因为程序很傻,它不会有很多的逻辑和智能的内容,它只可能去做if else,for loop和recursion。后两者就是不断的重复做一件事情。 所有你认为难的题目,它本质上都具有重复性。最关键是找重复性。而业务代码,很多if else处理业务逻辑,大部分用蛮力解决。
张一鸣 阅读《普通生物学》,找到世界的本质。他做两个产品
公司出的对外的各种产品,受众为外面的大众。公司本身,给所有2C,今日头条,抖音等所有的东西化繁为简,变为普适的。
爬楼梯问题变形: # 条件一:步长有三种,1,2 ,3 # 条件二:相邻步伐数不能相同
322 零钱兑换 爬楼梯:上11级台阶,每一可以走1,2步,有多少种走法? 注意:有多少走法,最少需要走多少步和走了多少步是不同的问题。
有多少走法:f(n) = f(n-1) + f(n-2)最少需要走多少步:f(n) = min(f(n-1), f(n-2)) + 1走了多少步:f(n) = sum(f(n-1), f(n-2)) + 2相当于爬楼梯问题变种: 上11级台阶,每一可以走1,2,5步,问最少可以走多少步?
对于1,2两种步数,走到台阶n的最小步数: f(n) = min(f(n-1), f(n-2)) + 1
coins问题(最少需要的银币数): f(n) = min(n - coins[i]) for i in coins + 1
int ans = INT_MAX; // 为什么要这么写?
最少steps: f(n) =sum(f(n - steps[i])) <- for i in steps