算法是定义良好的计算过程,通过一系列的计算步骤将输入数据转换为输出结果。首先第一点,算法本身是面向过程的,给定输入得到输出,与对象无关,所以用C语言来学习比较合适。然后,所谓定义良好是指算法必须包括三要素:输入、输出和计算过程。那么有没有不包含三要素的算法呢?首先看有没有没有输入的,产生随机数比较像,调用Rand函数得到一个随机的数字,但是实际上计算机的计算都是确定性的,产生的所谓伪随机数是以当前时间为种子(也可以自行指定)经过一系列计算得到,也就是算法不能做到“无中生有”;再看能不能没有输出,这里需要指出的是所谓输出不应该局限于返回计算结果,而是返回计算结果或者引起系统的某些变化都是输出,那么从节约的角度考虑,估计没有谁会让一个“泥牛入海”的算法存在吧;计算过程自然也是必不可少的,哪怕只是一直返回常量或者赋值这样简单的运算。
从正确的角度,算法应当对任意给定的输入都能完成计算过程并给出正确的结果。相反的,错误的算法则有两种可能,不能终止计算过程(迭代不能结束或者死循环)或者结果错误。但是并不是所有能够使用的算法都是正确的,有一些实际问题可能没有必然解或者解法过于复杂而寻求简单的方法,那么就可能要容忍一定的错误概率(书中以大质数为例)。这里还应当补充,结果正确应当指达到计算精度的要求,毕竟物理环境是模拟量,而计算机是离散系统,而且在迭代过程中有计算精度的限制,除了计算PI值这样的挑战问题,没有人会让程序一直无休止的跑下去,得到够用的结果就好。
数据结构是存储和组织数据的一种方式,以便于对数据进行访问和修改。结合面向对象的概念,数据结构实际上还可以理解为对物理世界的抽象,即类的概念,当然是简化版的,因为数据结构只有类的成员变量,而没有类的方法,但是通过数据结构+面向某个特定数据结构的算法组合,完全可以实现面向对象的功能。可见C语言虽然被称之为面向过程的语言,但是其设计是完备的,只是它把这些自由赋予了使用者而已。
算法设计需要考虑的首要指标是效率,包括时间和空间开销两个方面,通常情况下由于内存足够,我们会比较关注算法的时间开销,但是对于嵌入式内存受限或者处理海量数据时则会将内存开销放到更加重要的位置优先考虑,并且,这两点通常情况下是很难达到同时最优的,一般会主要关注一项而牺牲另一项。除此以外,现在的处理器都是多核,并行处理越来越重要,那么在算法设计时考虑线程安全将能够使其应用更加方便和高效(否则只能在多线程程序中通过进入算法前后加锁的方式保证安全);在团队协作中,算法的可读性和可维护性有时候会比算法效率本身更有价值。
BSKER于2011.10.12