第一章 算法简介
- 算法:算法是指一组完成任务的指令,任何代码片段都可称为算法;
- 二分法查找:查找对象是有序数组,运行时间 O(log n),查找的对象数组越大优势越明显;
- 算法的速度:指的是随着操作数的增加,算法运行时间的增加;
第二章 选择排序
- 内存的工作原理:数组和链表,其中数组的特点,元素有序,内存块是连续的,支持随机访问,但是插入和删除比较慢;链表,元素内存块是不连续的,内存块也是有序的,但是不支持随机访问,只支持顺序访问,插入和删除速度快;
- 选择排序:运行时间为 O(),基本思想是,每次从剩余的元素中找出最大的,然后添加到另一个空的数组中,并且在原数组中删除该元素;
第三章 递归
- 递归的本质:在方法自身调用自己
- 递归的构成:基线条件和递归条件,基线条件是使递归调用停止的条件,递归条件是调用需要满足的条件;
第四章 快速排序
- 分而治之:将大问题不断分解,直到不能再分解,在这个过程中寻求问题的解,例如土地划分问题;
- 快速排序:基本思想,每次从数组中的元素中找一个基准(可以是随机),通过和这个基准比较,然后将小于基准的移动到基准的左边,大于基准的移动到基准的右边,不断分割循环,直到不能分割,不能分割的时候,将所有的子集拼接起来就获得了大小顺序已经排好了的数组,其本质是分而治之。运行时间是 O(n*log n),最糟糕情况下运行时间是 O();
- 运行时间的计算方法,每次有多少个元素参与操作,比如是a,总操作次数是b,则总的运行时间为 O(a*b);
第五章 散列表
- 散列表:散列表是一种映射;
- 散列表的应有场景:①散列表用于查寻(电话号码,账户登录信息核对等,特点速度快);②防止重复(投票);③散列表应有与缓存(缓存数据一般在散列表中);
- 散列表的冲突:合理的散列函数可以使数据均匀的分布在散列表的内存;
- 散列表的性能:平均情况下,散列表的运行时间是 O(1),散列表的填充因子一般不要超过0.7;
第六章 广度优先搜素
- 广度优先搜索的目的:是一种用于图的查找算法,计算两个节点之间最短路劲;
- 广度优先搜索的应用案例:①编写国际跳棋AI,计算最少走多少步就可以获胜;②编写拼写检查程序,计算最少更改多少处地方就可以更改完所有的错误;③根据自己的人际关系网,找到关系最近的医生;
- 队列:先进先出的数据结构;
- 广度优先算法的代码原理:按层搜索,具体是,只要对列不空(循环条件),就开始循环拿要查找的元素和第一层的所有元素进行对比,如果相同,则返回这元素的信息或者返回true,跳出循环,循环结束,如果匹配不上就继续循环;
- 广度优先的运行时间:O(人数+边数);
第七章 狄克斯特拉算法
- 狄克斯特拉算法目的:搜索加权图下的最便宜路径(不一定是最短路径);
- 狄克斯特拉算法的步骤:
概念—开销:从起到到该点的累计权重为该点的开销;
①找出开始节点(S)的最便宜的邻居节点(A),即可在最小的开销下可以到达的路径;
②计算邻居节点(A)的邻居(A1,A2,A3…)的开销,更新这些节点(A1,A2,A3…)的开销,具体程序为,如果经过A节点的到达其邻居A1,A2,A3…的开销比通过其他路径达到这些点的开销小,则将这些开销记录为这些节点的开销,如果通过A点的开销更大,则将这些点的开销更新为更小的;
③重复①和②,知道遍历完所有的节点,也就是到达目的节点(D);
④计算最终路径;
第八章 贪婪算法
- 贪婪算法的核心思想:每步都选择最优解,最终得到的就是全局的最优解(不一定,但是八九不离十);
- 应有案例:①背包装东西问题;②集合覆盖问题;
- 代码案例:集合覆盖问题之——确定广播台问题的代码步骤:
①创建一个散列表,包含所有要覆盖的州(列表中不可重复);
②创建广播台的散列表,包括每个广播台所覆盖的州的键值对(这样的键值对有很多);
③程序原理:外层循环条件,只要需要覆盖的州集合不为空,就一直循环;接着进行内层循环,对每个广播电台进行循环,找出集合中剩余没有被覆盖的州中,覆盖了最多的剩余州的广播电台,此轮的内层循环结束,把这个电台添加到要选择的最佳电台集合中,接着外层循环; - NP(集合覆盖问题):最佳的解决方法是近似算法;
- 贪婪算法是非常好的近似算法,易于实现,运算速度快;