作为软件工程师,我们在谈论自己时,总会认为自己是所谓的高科技行业从业者,但是如果观察自己的日常工作,时常会觉得似乎和真正的科技也没有什么关系。所以究竟什么是科技?我们要如何来定义我们每天的工作?

我认为宏观意义上的科技可以被拆解成三个概念:科学(Science),技术(Technology)和工程(Engineering)。

科学是观察客观世界以发现既有的自然规律,技术是组合自然规律以发明新的改造客观世界的方法,工程是发挥技术的能力以合乎客观世界要求的方去改造它。

欧姆定律,麦克斯韦方程组是科学的发现,整个电子产业的基石全在于控制电子的运动与电场的传递,电子的运动建构了存储和计算的能力,电场的传递建构了通信能力。电子的运动一定会遵守欧姆定律,电场的传递一定会遵循麦克斯韦方程组。

在自然规律的基础上,人们将电磁感应与过去的蒸汽机技术相结合发明了发电机技术。如果宇宙仅有地球存在智慧生物,那么第一台发电机的发明是真正创造了一个过去不曾有过的事物。但发电机的发明者不见得一定要制作出一个性能优异的实际发电机产品,可以只是一个原型,甚至可以只是提出了一种概念。冯诺伊曼也并没有实际去动手做出一个以他名字命名的结构下的计算机,但他的确发明了现代存储程序型计算机的概念。

要将一个抽象的计算机设计落地成为一个实际可用的计算机设备中间还是有很长一段距离,需要考虑非常多复杂的情况,例如成本,规格,安全性等。工程所做的,就是发挥实验室中的技术到非理想的现实环境中去。我们经常说的某个技术不具备可行性,通常其实是指这个技术本身虽然可行,但是在工程上不可行。

客观世界的复杂性根源来自事物彼此之间是有相互作用和联系的,改造客观世界的方法也在于利用事物的这一特点加以「组合」。自然规律是对元素周期表的组合而产生的现象,技术是在组合自然规律创造新的方法,而工程又是在组合各类技术创造出实际的产品。

人类的大脑无法并行地去进行多条件下的逻辑思考,所以往往会先剔除所有其他因素,假设一个理想的环境,从而得以专注于在此环境下得出仅适用于该环境下的某种规律,并美其名曰科学的「简洁性」。从事科学研究的人把对于非理想环境的思考移交给了去实际发明技术的人,而从事技术发明的人同样会倾向于简化问题,将复杂性移交给了那些真正去落地的工程师。这就是工程为什么会如此复杂的原因所在,他本身的目的就是去管理复杂性

在工程学领域中,软件工程又可能是其中最复杂一类工程。其根本性原因在于软件开发是一门个体创造性太强的工程。今天如果你要去制作一部手机,在供应商和成本的制约下,会让你在工程上并没有太多选择,这也是为什么所有手机厂商制造的手机参数和外观都差不多的原因。而软件就不同了,每个公司首先编程语言就可以有不同的选择,其次不同的发展阶段也需要有不同的软件架构,再者还可以有各种第三方库的选型。同样是一个业务需求,让100个工程师去实现,可能会有100种不同的技术选型组合,实际到编码层面又有更为不同的风格和设计差异。最致命的问题是,这100种做法很可能都同时是 make sense 的方案。

软件相比于硬件还有一个特点是其生命周期极长。人或许会几年换一次硬件,无论是电脑还是汽车,但有可能几十年就用同一种软件。与此同时不同软件之间因为需要彼此交互,还有着固定的接口和协议,所以软件的升级和更换还存在一个兼容性的问题。说到这里,或许有人会发现软件和人类自身是极为相似的。

1968年北约首次定义了软件工程的概念,而这一年苏联入侵了捷克斯洛伐克,中国正在大搞文革。人类浪费了大量时间在处理各种没有任何意义的内部外部矛盾,如果人类的上层也有一个「人件开发者」,那么他的架构能力肯定非常一般,但同时也非常厉害,至少能让如此混乱的人类存活几万年到今天。软件工程内部的矛盾亦如人类社会的矛盾,甚至有时人类社会自身的政治也会被带入到软件内。我们可以在 iOS 和 Android 的设计里看到共和党和民主党的影子。大量的软件工程师花费了大量的生命仅仅就为了让某个软件同时能够跑在多种设备上,但如果这些设备能够一开始就使用同一种接口,可能就没有这么多事情。软件也不是没有做此类的事情,大量的软件协议就是为此而生,这有点接近于国家间的贸易协定,制定协议的工程师就如何现实里的政客。

所以回到文章开头的问题,为什么软件明明是人类至今最高科技文明的产物,而作为软件工程师的我们却很难从日常工作中感受到高科技的工作氛围?因为今天我们编写的程序,和第一台计算机上的纸带其实没有任何本质区别,而我们日常工作所在解决的复杂性问题,恰恰是由于前人在试图解决复杂性问题时所创造的复杂性,而这其实和计算机科学本身没有任何关系。如果软件的复杂性能够被彻底消除,人类社会也就不会存在如此多的政治矛盾,但亦如同复杂性造就了人类文明的璀璨一样,正是高创造性的软件开发才能爆发出今天我们所见到的精彩纷呈的软件革命。