数据结构与算法概述
算法
算法的概念:
-
- 算法是计算机处理信息的本质,因为计算机程序本质上是一个算法来告诉计算机确切的步骤来执行一个指定的任务。一般地,当算法在处理信息时,会从输入设备或数据的存储地址读取数据,把结果写入输出设备或某个存储地址供以后再调用。
- 算法是独立存在的一种解决问题的方法和思想。
- 对于算法而言,实现的语言并不重要,重要的是思想。
算法的5大特性:
-
- 输入:算法具有0个或者多个输入
- 输出:算法至少有1个或多个输出
- 有穷性:算法在有限的步骤之后会自动结束而不会无限循环,并且每一个步骤可以在可接受的时间内完成
- 确定性:算法中的每一步都有确定的含义,不会出现二义性
- 可行性:算法中的每一步都是可行的,也就是说每一步都能够执行有限的次数完成
算法效率衡量:
-
-
消耗计算机资源和执行效率(不推荐,不直观)
-
计算执行耗时(适当推荐,因为受机器和执行环境的影响)
- 可以利用python内置的timeit模块
- timeit模块:该模块可以用来测试一小段Python代码的执行速度。
- Timer类:class timeit.Timer(stmt='pass',setup='pass')类是timeit模块中专门用于是测量小段代码执行速度的类
- stmt参数:是要测试的代码语句
- setup参数:是运行代码时需要的设置
- timeit方法:timeit.Timer.timeit(number=1000000)方法返回执行代码的平均耗时,一个float类型的秒数。number参数是测试代码时的测试次数,默认为1000000次
- 示例:
# coding:utf-8 from timeit import Timer def t1(): a_list = [] for i in range(10000): a_list.append(i) def t2(): a_list = [] for i in range(10000): a_list += [i] timer1 = Timer(stmt='t1()',setup='from __main__ import t1') timer2 = Timer(stmt='t2()',setup='from __main__ import t2') print('执行t1平均耗时:%s秒'%timer1.timeit(10000)) print('执行t2平均耗时:%s秒'%timer2.timeit(10000))
- 执行结果:
执行t1平均耗时:10.921018191000002秒 执行t2平均耗时:11.956596394000002秒
-
时间复杂度(推荐)
- 评判规则:量化算法执行的操作/执行步骤的数量
- 最重要的项:时间复杂度表达式中最有意义的项
- 大O记法:就是使用时间复杂度衡量算法好坏的表现形式
- T(n) = O(最重要的项)
- 比如操作数量为3n²+2n+1,大O记法表示为:T(n) = O(n²)
- 基本计算规则:
- 基本操作,即只有常数项,认为其时间复杂度为O(1)
- 顺序结构,时间复杂度按加法进行计算
- 循环结构,时间复杂度按乘法进行计算
- 分支结构,时间复杂度取最大值
- 判断算法效率时,往往只需要关注操作数量的最高次项,其它次要项和常数项可以忽略
- 未作特殊说明,时间复杂度都是指最坏时间复杂度
- 常见时间复杂度之间的关系:
- O(1) < O(logn) < O(n) < O(nlogn) < O(n2) < O(n3) < O(2n) < O(n!) < O(nn)
- 注意,经常将log2n(以2为底的对数)简写成logn
- 示例:已知a+b+c=1000,且a^2+b^2=c^2(a,b,c 为自然数),如何求出所有a、b、c可能的组合
- 算法1:
for a in range(0, 1001): for b in range(0, 1001): for c in range(0, 1001): if a**2 + b**2 == c**2 and a+b+c == 1000: print("a, b, c: %d, %d, %d" % (a, b, c))
时间复杂度:T(n) = O(n*n*n) = O(n3)
- 算法2:
for a in range(0, 1001): for b in range(0, 1001-a): c = 1000 - a - b if a**2 + b**2 == c**2: print("a, b, c: %d, %d, %d" % (a, b, c)
时间复杂度:T(n) = O(n*n*(1+1)) = O(n*n) = O(n2)
- 算法1:
-
数据结构
数据结构的概念:
-
- 数据:数据是一个抽象的概念,将其进行分类后得到程序设计语言中的基本类型。如:int,float,char等
- 结构:数据元素之间不是独立的,存在特定的关系,这些关系便是结构
- 数据结构:指数据对象中数据元素之间的关系,即对于数据的组织方式称为数据结构。数据结构解决的是一组数据如何保存,保存形式是怎样的问题
- 内置数据结构:Python给我们提供了很多现成的数据结构类型,不需要我们自己去定义的数据结构叫做Python的内置数据结构,比如列表、元组、字典。
- 扩展数据结构:Python系统里面没有直接定义,需要我们自己去定义实现这些数据的组织方式,这些数据组织方式称之为Python的扩展数据结构,比如栈,队列等。
数据结构案例:
-
- 需要存储一个班级学生的信息,这些数据该如何组织?如何快速的通过姓名来查找具体学生的信息,时间复杂度是多少?(分别选用列表和字典进行存储)
- 列表
stus = [{'name':xxx,'score':xxx},{'name':xxx,'score':xxx}...]
获取某个学生信息时,就要遍历这个列表,其时间复杂度为O(n)
- 字典
stus = { 'zhangsan':{'score':xxx}, 'lisi':{'score':xxx}, ... }
可直接通过学生姓名快速获取到学生信息,其时间复杂度为O(1)。
- 列表
- 需要存储一个班级学生的信息,这些数据该如何组织?如何快速的通过姓名来查找具体学生的信息,时间复杂度是多少?(分别选用列表和字典进行存储)
算法与数据结构的区别:
-
- 数据结构只是静态的描述了数据元素之间的关系
- 高效的程序需要在数据结构的基础上设计和选择算法
- 程序 = 数据结构 + 算法
- 总结:算法是为了解决实际问题而设计的,数据结构是算法需要处理问题的载体