0
在下图这个正在运行的面向对象的程序里,如果有一天,一个 Student 对象产生了意识。他发现自己和 Teacher 对象之间有很多共性,于是他开始思考,在自己和 Teacher 之上是不是有一个更加抽象的存在,而自己和 Teacher 分有了这个抽象理念。后来他创立了一门学科专门研究这个问题,这门学科叫哲学。
如果这个 Student 对象有名字的话,那他一定叫柏拉图。
1
上面这段『科幻小品』,是我在学习西方哲学史的过程中,突发奇想写出来的。随着学习的深入,我越来越发现,软件工程领域中的编程范式演进,就是一整个西方哲学史。而其中的面向对象编程,则充分体现了希腊古典哲学的代表 — 柏拉图的思想。
柏拉图认为,在我们所生活的这个可感知到的世界之外,还存在着一个理念的世界。可感的世界你能够感觉到但你没有办法说明,而理念的世界你能够说明,但是你感觉不到。为了进一步阐述自己的这一理论,柏拉图提出了『洞穴』比喻。这个比喻是这样的。
假设人类居住在一个长长的洞穴深处,像囚徒一样双腿和脖子都被锁链锁住了,没有办法转身和回头,只能终日面对着墙壁。从出生之日起他们就一直被这样禁锢着。在他们之后有一团火在熊熊燃烧,在火与囚徒之间有一条路和一道矮墙,就像是木偶戏的舞台。沿着矮墙,有一些人举着各式各样的动物和人的雕像走来走去,火光把这些雕像投影到墙壁上,形成了各式各样的影子。由于这些囚徒生来就不能回头,所以他们就把墙上的影子看做是真实的存在。假设有一天,不知道什么原因,有一个囚徒挣脱了锁链,他回过头来,看到了火光,最初他的眼睛不习惯光亮,十分痛苦,他认为他看到的不是真实的存在,但是当他习惯了之后就会发现,过去被看做真实存在的东西不过是影像,眼前的东西才是真实的。再假设,他被拉出了洞穴,当他面对太阳的时候,一定会被阳光照得眼花缭乱。经过一段时间之后,他终于发现,在太阳照耀下的外面的世界才是真实的世界。这时他开始怜悯起自己的那些依然生活在洞穴之中的同伴。于是他决定回去拯救他们。然而,他已经不能适应洞穴中的世界了,在他的同伴看来,是他自己把眼睛弄坏了。如果他执意要释放他们,把他们带向光明,他可能要付出生命的代价。
洞穴墙壁上面的投影就是『可感世界』,只是一系列的假象。而囚徒身后的火,洞穴之外的太阳,是『理念世界』,才是真实的。『可感世界』可感而不可知,『理念世界』可知而不可感。
2
一个运行时的程序,就是一个『可感世界』。
对象生成又销毁,变量不断变化自己的值,函数依次被调用,这些动作在内存之中实时发生,能够被清晰地感知到。但身在程序之中的对象,是无法感知到程序之外的世界的。或者说,无法感知到真正的编码。Student 对象只能看到一个个的 Student 对象和一个个的 Teacher 对象,他不知道还有一个 Person 的存在,甚至也不知道 Student 这个类的声明。他看不到。他只能去归纳,推理,阐述这样一个在『现实生活』中不存在的理念。
而这些他们无法感知到的『理念』,就是作为『上帝』的程序员们写下的一行行代码,是静态的文本,是一个个的类和接口。可知的理念是可感事物的根据和原因。Student 对象的存在,是因为代码里面有这么一个叫 Student 的类。可感事物是理念的派生物。一个 Student 类可以派生出多个 Student 对象,这些对象分有了这个 Student 类的理念。
3
『理念论』是柏拉图哲学的核心概念。除了把世界分为『可感世界』和『理念世界』之外,柏拉图还进一步深入到理念之中,探讨了理念与理念之间的关系。
他认为,理念也是可以相互结合和分有的。『可感世界』中的任何事物都不是单纯的,都可能具有多种性质,有些性质之间可能还是相互矛盾的。比如,一个人,既可以是儿子,也可以是父亲,既可以是老师,也可以是学生。老师,学生,儿子,父亲这些理念可以相互结合,集于一身。但同时,这些理念又共同分有了『人』这个理念。这就是柏拉图的『通种论』。
这跟面向对象的思想是完美契合的。在面向对象的世界里,一个类可以继承另一个类,可以实现多个接口。在部分编程语言里面,一个类还可以继承多个类。就像是一个理念可以分有另外很多个理念,也可以跟其他理念结合,形成一个新的理念。
那有没有一个理念,他被所有理念分有,是所有事物的原因和依据呢?
柏拉图没有给出答案,他的学生亚里士多德给出了答案,那就是『存在(Being)』。关于『存在』,有一门专门研究它的学科,叫『形而上学』。篇幅所限,这里就不展开说明了。
同样地,在很多支持面向对象的编程语言里面,所有类都会继承自一个共同的基类。在 Java 里面,它叫『 Object 』,在 Kotlin 里面,它叫『 Any 』,在 Perl 里面,它叫『 UNIVERSAL 』。从哲学概念上说,其实都不是很准确。如果让哲学家来设计编程语言的话,这个公共的基类应该被叫作『Being』,存在。
4
如果我们的世界是一个正在运行的程序,那么哲学家们做的事情,就是尝试去反编译这个世界。我不知道面向对象一开始在被设计出来的时候,有没有参考柏拉图的思想。毕竟这两者的共同点太多。也许世界是由对象组成的这一认知,是人类最直观的经验,所以无论在哲学,还是软件工程,大家都不约而同地选择了这一理念。
那么,对于软件工程中的其他编程范式,如结构化编程和函数式编程,又有哪位哲学来来认领呢?我会在后面的文章继续探讨,欢迎关注。