# 什么是算法?
# 算法🔍💡
- 1️⃣ 需要解决具体问题
- 2️⃣ 设计解决问题的具体流程
- 3️⃣ 使用可量化指标对处理流程进行评估
针对一个具体的问题,可以将其分解为多个可执行的步骤。虽然这些步骤可能存在重复,但最终都能够达到问题的解决状态。
由于不同人对问题的分解步骤可能不同,因此需要使用评估方式来评价这些步骤的好坏,例如评分可以分为好、中、差。
因此,算法不仅包括解决问题的具体流程,还包括使用可量化指标来评估流程的有效性。
# 算法的分类🗂️🤔
- 1️⃣ 分类非常多
- 2️⃣ 对于新手学习非常重要的分类
- 1️⃣ 明确知道如何计算的流程
- 2️⃣ 明确知道如何尝试的流程
算法有很多分类,但具体如何解决问题,听起来就像是一个哲学问题。
然而,在计算机中,解决问题一定依赖于具体的数据结构。
数据结构是底层逻辑的基础,通过在数据结构上设计一些流程来解决问题,这就是所谓的算法。
算法的分类非常多,但对于新手学习来说,有两个分类尤其重要:
- 1️⃣ 明确知道如何计算的流程
- 2️⃣ 明确知道如何尝试的流程
# 第一类:明确知道怎么算的流程🔢🧮
例如:
- 相反数是取反加一
- 3 + 4
- 3 * 6
这些都是明确知道如何计算的具体问题。这个过程利用了电子设备的快速特性,替代了手动计算的过程。这就是明确知道如何计算的算法分类。
# 第二类 明确知道如何尝试的流程🔢🧮
第二类算法是明确知道怎么尝试的流程,这种算法更加重要。虽然我们不知道如何算出一个问题的确切解法,但是我们知道如何尝试,如何去试图找到一个解法。
举个例子:
- 我们不知道一个数所有的因子怎么算,但是我们可以试着将所有可能的因子尝试一遍,从而找到所有的因子。
在图灵之前,已经存在了一些计算工具,比如十进制的计算工具木制的算盘,但是它们并不是计算机,只能加快计算的速度。在图灵之前,所有的计算器只能做一件事,就是利用已知的算法进行计算。
第一个程序员其实是一个女性,诗人拜伦的女儿,她当时在那种机械结构的计算机上用打孔的方式,编写程序。当时的计算机只能使用已知的算法,无法进行试错。
图灵通过破解德军的密码,发明了一种如何试错的算法,这是一种全新的思路,为今天计算机的基础奠定了坚实的基础。因此,图灵被誉为计算机的祖师爷,而图灵机被视为计算机的原型。通过明确知道怎么尝试的流程,计算机科学变得更加有魅力,成为了一门科学。
# 举个例子
题目:
给定一个参数 N, 返回: 1! + 2! + 3! + ... + N! 的结果。题目解析
同学 A(N)
- 计算 1!= 1
- 计算 2!= 1*2
- 计算 3!= 1*2 *3
- ...
算出所有的阶乘,进行累加,不加任何优化。
同学 B(N)
- 计算 1!= 1
- 计算 2!= 1!*2
- 计算 3!= 2! *3
- ...
每次阶乘借用上一次的结果,每次阶乘只乘一遍
我们明显可以感觉到 B 同学设计的算法好一些,虽然我们还不知道什么是时间复杂度。
算法并不神秘,此时我们已经迈入算法的大门了!
# 时间复杂度
我们以 同学A 的方法为来讲解下时间复杂度。假设我们的输入是N,那么我们得到最后的结果的计算量与我们的输入数据大小有什么关系呢?我们可以根据我们的算法流程,分析出一个关系的公式。
同学 A(N)
- 计算 1!= 1 1!结果为1,直接返回,不需要计算
- 计算 2!= 1*2 2!计算 1 * 2,计算量为 1 次
- 计算 3!= 1*2 *3 计算 1 * 2 一次,用结果 * 3 计算 1 次,计算量为 2 次
- ...
- 计算 N-1!= 1*2 *3.....*N-1 以上类推,需要计算 N-1-1 次,即:N-2 次
- 计算 N!= 1*2 *3.....*N-1*N 以上类推,需要计算 N-1 次,即:N-1 次
通过我们分析每一步的计算量,我们可以知道计算量的和为等差数列,使用等差数列求和,使用公式:
求得我们计算的总和为:(1/2)N^2 - 1/2,得到公式后,我们需要忽略公式中N的系数和常数,并且只取N的最高项,我们可以知道最高项是 N^2。在算法中我们使用大O()表示算法的时间复杂度,括号内的表示使用我们之前的公式中取到的最高项。所以我们A同学的算法的时间复杂度就用O(N^2)表示。
