邓俊辉数据结构与算法学习笔记-绪论


打算用1个月的时间,系统的学习一下清华大学邓俊辉老师的《数据结构与算法》,不仅仅学习相关知识点,更想把握算法和数据结构的深刻内涵。

一.绪论

1.1 如何理解计算?

研究计算,在于挖掘其中的规律和技巧,实现更高效和低耗的计算,可以看作一个闭环。

下面这句话很好的阐述了计算的本质。所谓计算机科学其实可以被称为计算的科学,计算机只是研究计算的手段,最终目的是为了研究计算中的规律和方法,实现更高效和低耗的计算。

computer science should be called computing science, for the same reason why surgery is not called knife science.     -E.Dijkstra

具体来说,计算等同于信息处理,它的特点是借助某种工具,遵照一定规则,以明确机械的形式展开。这种工具,就是计算机或者广义的来说,就是信息处理工具。那么这种规则,狭义的可理解为算法,明确性和机械性也是算法的显著特点。

展开来说,算法,也就是特定工具(计算机)下,旨在解决特定问题的指令序列

它的主要特点如下:

  • 输入:待处理的问题
  • 输出:处理完的答案
  • 正确性:确实可以解决指定的问题
  • 确定性: 任意算法都可以描述为一个由基本操作组成的序列
  • 可行性:每一个基本操作,都可以在常数时间内完成
  • 有穷性:对于任何输入,经又穷次基本操作,都可以得到输出

对于有穷性可能不太直观,举一个有趣的例子

上面是一个Hailstone序列的一个表达式,从分段函数来看,很好理解。也可以很容易的编写程序计算指定序列的个数。当然强调的不是这个,可以计算,Hailstone(7)时,其序列个数较大,而当Hailstone(27)时,其序列个数特别巨大, Hailstone(42)序列个数只有十余个。当n取不同值时,其序列长度并没有明显规律。事实上,研究者目前仍无法判定对于任意的n,Hailstone(n)到底是有穷的还是无穷的,显然,这个程序由于不满足有穷性,该程序并不是一个算法

上面论述了算法的基本特点,那什么才是一个好算法?

如上图,它得满足正确性、健壮性、可读性、效率。

这里说一下效率:

所谓效率,就是要求算法速度能尽可能的快,并且耗费存储空间尽可能的小。也就是俗语说的”要想马尔跑得快,还想马尔不吃草“。也就是说,解决问题的程序是由算法和数据结构有机结合在一起的,但这并不能实现开头所说的,高效和低耗的计算,还需要效率。也就是

(algorithm+structure)*efficiency=computation

1.2 算法的衡量

上节说到,算法和数据结构的有机结合,还需要进行效率的判断,这样才能实现高效和低耗的计算。

有句话很有意思,说明了衡量的重要性

To measure is to know ,If you can not measure it,you can not improve it.    -Lord Kelvin

那么,如何衡量有效性呢?

暂时忽略掉存储空间,从时间角度分析,如果将实例作为输入,显然不显示,更好的策略是将规模作为输入。

针对特定算法,不同实例:

将规模作为输入也有缺陷,即同一问题同等规模的不用实例,其成本也不相同。因此可以转而去求解所有实例中,成本最高的。

针对特定问题,不同算法:

显然,为了给出客观评价,抽象出一个理想的平台或模型比较可靠。

那么,图灵机和寄存器就是这样一个而理想的平台或者模型

它将算法的运行时间具体到算法在图灵机或者寄存器中需要操作的基本次数,这样就可以客观评价了。、

1.3 大O记号

如果将上一节的图灵机或者寄存器比作直尺,则大O记号就是直尺上的刻度。需要强调的是,只需对大O表示的含义有一个宏观的把控,看重长远和潜力,即数据量更大的时候的表现,不要纠结细微不足和旁支末节。

在来一句有意思的话

Mathematics is more in need of good notations than of new theorems.    -Alan Turing

对于多项式划重点:常数项可忽略,低次项可忽略

大O基本上确定了f(n)的上界,还有其他的符号确定了下界,或者确定到一定范围内。由于一般考虑最坏的情况,所以考虑上界。

1.3.1 常数时间复杂度分析

对于常数操作的时间复杂度比较好分析,但是应该注意一些特殊情况,如下,包含循环、分支、子函数调用甚至递归结极,但具有常数时间复杂度。

解答:

1.循环结构的递增条件是1+n/2013,也就是说算法执行的次数不随n变化,无论n怎么变,其都执行2013次,显然虽然它具有循环结构,但是其仍然是常数时间复杂度。

2.其余的判断条件无法满足,即便其判断内部的执行体有函数调用,递归等,其仍具有常数时间复杂度。

所以对于程序时间复杂度的估算,不能完全停留和依赖于其外在的流程结构;更为准确而精细的分析,必然需要以对其内在功能语义的充分理解为基础。

1.3.2 对数时间复杂度分析

稍微解释一下:

对于对数时间复杂度的分析,1.常底数无所谓,因为可以换底。2.常数次幂无所谓,可以前置。

c接近于0,那么这类算法时间复杂度则无限接近于常数

1.3.3 指数时间复杂度分析

指数算法的计算成本增长很快,通常认为不可接受。多项式到指数,是算法从有效到无效的一个分水岭。

总的看一下吧:

o(1)<o(logn)<o(sqrt(n))<o(n)<o(nlogn)<o(n2)<o(n3)<o(2n)

总结

基本上是泛泛的谈一下,还没涉及到重点!本章还有1部分算法分析的内容,这是重点,过俩天更新。


免责声明!

本站转载的文章为个人学习借鉴使用,本站对版权不负任何法律责任。如果侵犯了您的隐私权益,请联系本站邮箱yoyou2525@163.com删除。



 
粤ICP备18138465号  © 2018-2025 CODEPRJ.COM