-前言-
软件杂谈是大叔打算写的关于软件的随笔系列,多数是在开车行路中冒出的想法,又怕年纪大了忘却,便记下来。
有些人天生就喜欢写作或记录生活,这当然是个很好的习惯,而我却不太擅长。在我看来,静下心写一些东西是很奢侈的事情,每天奔波,很少能给自己挤出一点时间。
最近流行一句话:“贫穷限制了你的想象力”。忙碌又何尝不是?忙碌更像是鸦片,会使人习惯甚至麻木。你看,这世界上是不是中国人最勤劳忙碌,也恰巧是中国人最缺乏想象力,忙得没时间思考,没时间想象。
大叔很忙,可还有那么一个私密时间属于我独有,那便是开车的时候,安静且没人打扰。
这还要“感谢”我大西安的交通拥堵,别人抱怨,我却很享受。每天至少在车里度过两个小时,除了思考,还能做些什么?
当然,这种享受要对老司机来说才是这样,因为只有老司机才能腾出大脑,边开车边思考。
大叔搞软件技术20多年,驾龄15年,当然是老司机了(相信你没有想歪)。
言归正传,既是杂谈,便无有顺序可言,想到哪里聊到哪里。也无有题材限制,只要跟软件技术相关,都可以聊。
这一篇我们先聊一个词--“解耦”。
选解耦为关雎,还是有原因的,因为在大叔眼里,解耦太重要了。
重要到什么程度?基本上只要掌握好解耦,软件开发内功的任督二脉就基本打通了。
-概念-
解耦这个词译自英文decouple,翻译的非常好。
从词义上看:
解者,拆也,分也,离也,断也。
偶者,索也,合也,并也,缘也。
解耦,顾名思义就是降低软件体之间的耦合度,直至彻底断耦的过程。
我们这里所说的软件体,是指具有相对独立性的软件功能集合。可以理解为某个函数体或者模块,或更多的指可重用的服务和组件。
那么什么是耦合与耦合度呢?
所谓耦合,是指两个或多个软件体之间的依赖关系。耦合度就是这种相互依赖关系的强弱程度。
耦合度越高,软件体之间的牵连羁绊就越多,依赖性就越大,反之则反。
例如,一个组件,依赖于另一个组件才能够运行,那么就说这两个组件之间存在耦合。倘若一个组件依赖于它运行的环境才能够运行,那么就说这个组件跟环境之间存在耦合。
-思想由来-
解耦不是某种语言或者技术特有的概念,解耦是一种普遍存在的思想。
解耦的思想由来已久,早在软件可重用技术提出之前,硬件集成电路(IC)技术就普遍采取了解耦的技术。道理很简单,每一个集成电路模块在设计上必须具备独立性,标准性和解耦性,才能够像搭积木一样构建出复杂的系统。
伴随着软件可重用思想及相关技术的产生,接口和解耦的概念也应运而生。软件组件以及基于组件的开发(Component Based Development - CBD)要求组件能够像集成电路一样独立存在,通过事件松散耦合。由此发展出的一系列组件模型,都是解耦思想的完美实例。例如Enterprise JavaBeans (EJB)模型,Component Object Model (COM)模型,.NET模型等等。
在面向服务的架构(Service Orientation Architectures - SOA)中,也需要软件服务相互独立,没有耦合。
还有这些年流行的微服务,前后端分离,也是这样。
云计算以及云平台,也处处体现着解耦思想。例如,基础设施即服务 (IaaS)、平台即服务 (PaaS) 和软件即服务 (SaaS)等技术中都体现着热插拔,松耦合,资源动态分配整合的特点。
-耦合的影响-
软件体之间存在耦合,会增加软件实现的复杂度。
耦合像一种无形的力量,束缚着软件结构的健康。不经思考的随意耦合,可能造成内部逻辑混乱,难以纠正,有如三千烦恼丝,剪不断理还乱。
高耦合度的软件系统,阅读起来一定困难,维护成本一定提高,复杂度随之也高,也会导致质量的下降。
佛教思想中有十二因缘的理论,讲述由无明引起的环环相扣、因果相随的轮转生死过程。串接苦趣每一环节的是缘,要想获得自由、脱离生死,就要认识缘断了缘。
类似的,耦合的本质也是缘。而正是这种牵绊,造成系统复杂乃至生出种种问题和痛苦。
-解耦的本质-
既然耦合的本质是缘,那么解耦的本质就是断缘,并通过断缘提升软件体的自由。
没错,是自由!
自由会带来活力,自由会引发包容开放,自由会促进事物健康发展。
没想到这个充满人文思想的因素,在软件系统中也是这样。
一个国家缺少自由,必然会走向灭亡。一个软件系统缺少自由,必然会问题百出并导致失败。
原谅我这一生不羁放纵爱自由,大叔之所以把解耦放到第一篇来讲,也有这个原因,解耦太重要了,自由太重要了。
-解耦的方法-
实际上,软件体之间不可能没有联系,否则我们靠什么把它们串接起来。
我们要拆解的不是依赖关系,而是要打破对某个具体实相的依赖,也就是对某个具体的软件体的真实性的依赖。这句话不拗口吧?
怎么打破?答案就是抽象和接口。
通过抽象和接口,依赖关系的实体消亡,软件体除了自身表现出内敛性外,一切对外的认知都建立在抽象和接口之上。
不着相,保持自性清净,是通达精神自由的方法。在解耦层面,亦复如是。
当软件体之间彻底断耦,它们中的每一部分就处于独立存在的状态。我们甚至可以把其中的任何一个替换掉,而不会影响整体正常工作。对整个系统而言,也带来了更大的自由度。
我们时常听到的依赖倒置,控制反转,依赖注入,面向接口编程这些概念,都是在抽象和接口依赖的关系上建立和实现的。
其实你可能每天都在接触解耦,只是自己也要用好解耦而已。
-解耦的人文精神-
一个耦合度小的软件设计和实现,无论从结构上还是细节上都会带给人赏心悦目的感觉。这种由内向外透出的美感,很大程度上就源于解耦后的软件体所具有的独立性和自由性。
而独立性和自由性,正是现代文明中的人类追求的精神价值和目标。
正如陈寅恪先生题写在《清华大学王观堂先生纪念碑铭》中的十个大字:“独立之精神 自由之思想”,时刻提醒着我们要在求知的道路上树立独立自由的精神。
作为软件工作者,想写出好的软件,也需要力求把这种独立自由的人文精神赋予在软件作品当中。
不自由,毋宁死。此时,解耦就显得尤为重要。
希望大家能够理解并应用好解耦,写出层次清晰,结构灵活,质量可靠,优美的软件。
-2018.03.31 蘭山 -