2.1 可读的代码才是可维护的代码
昨天我从咨询工作现场回到办公室,与同事谈起他近期要参加的1K大赛。这种比赛是demo party的传统节目——demo party是一种极客聚会,黑客们会带着计算机、睡袋、能量饮料在巨大的舞台上待上整个周末。
从第一届开始,黑客们就互相较劲,在很多人认为过时的硬件上舞弄着疯狂的技巧来制作3D动画。
这种动画的一个典型约束是大小。在我同事要准备的比赛中,其名字1K意味着代码编译为二进制之后的大小不能超过1024字节。
对,你没听错——1024字节。为了把有用的程序装入这么小的空间,参赛者需要使用各种奇技淫巧。例如,一个使代码更紧凑的常见手段是让多个变量使用相同的名字——因为这样代码压缩得更好一些。太疯狂了。
生成的代码也同样疯狂。当他们将代码压缩到1024字节时,源代码已经面目全非了。你几乎认不出是使用了哪种编程语言!它基本上是一个只写(write-only)代码库——一旦开始压缩,你就无法再改变功能,因为你分辨不出要编辑什么,也不知在哪里编辑和如何编辑。
给你一个鲜活的例子体会一下,这是最近JS 1K比赛中实际提交的代码,选用的语言是JavaScript,而它需要装到1024字节内:
当然,这种情形比一般软件公司中的极端情况还要高几个量级。但我们都在工作中见过让人头大的代码。有时我们称这种代码为遗留代码,因为那是从别人那里继承下来并接手维护的——只是它太难维护了,每次试图去理解它都令人头疼。维护这种不可读的代码是一个苦差事,因为我们花了这么大精力去理解我们看到的代码。不仅如此。研究表明,较差的可读性与缺陷密度密切相关。
自动化测试是防止缺陷的有效保护。遗憾的是,自动化测试也是代码,其可读性也很容易变差。难以阅读的代码也就难以测试,导致更难为之编写测试。而且,我们编写的测试还远远达不到优秀的地步,因为我们需要围绕拙劣的结构、难懂的API调用及非测试友好的结构来组织代码。
我们建立的代码可读性(几乎令人咆哮)对代码可维护性具有可怕的影响。那么测试代码的可读性又如何呢?有多大差别,或者有差别吗?我们看个难读的测试代码的通俗示例,如代码清单2.1所示。
这个测试在检查什么?你敢说它很容易理解吗?想象自己是团队里的新人——你要花多久才能明白测试的意图?如果该测试突然失败,你要如何调查代码才能搞清状况?根据我对丑陋代码的感觉,我打赌你立即可以从这个烂测试中识别出一些可以改进的地方——可读性是一个常见的改进方面。