在侃侃而谈OO,侃侃而谈设计模式,侃侃而谈面向对象的诸多原则之前,我们首先应该掌握一点:封装。掌握好封装的原则和技巧之后,就算使用的不是OO语言,也能构造出框架优美的程序。将这些原则用在程序之外,也能得到出奇的效果。《设计规则-模块化的力量》(http://www.douban.com/subject/1737636/)将封装与模块化放在神坛的高位,它们配得上这个位置。这是我们解决复杂性问题的最基本的方法(没有之一)。
程序是一种复杂性系统。“道生一,一生二,二生三,三生(四,四生…)万物”。若将复杂性的根源当作“道”的化,那么这个“一”必然是封装。不同的程序语言以及由这些程序语言衍生的方法,则处于“二”的地位,比如 OO 设计范式、FP(函数编程)范式、分层的原则等等。OO设计准则,什么里氏替换原则,什么组合优先于继承,这些处于“三”的地位,具体的设计模式什么之类的处于“三”之后“四”的地位。
本人愚笨,至今尚记不清那些原则,如里氏替换原则是什么,那些这个模式那个模式怎么实现。设计模式中,俺只对策略模式感兴趣,对其它模式兴趣索然。实质上这些模式也好、准则也好,只是给我们提供了一种方法、一种工具去更好的实现封装。
复制和粘帖是封装的大敌,是丑陋代码的最大的坏味道。复制一份,就相当于增加了至少一个可变点,复制两份就相当于增加了至少两个可变点。为什么说“至少”呢,因为模块之间存在关联关系,导致一个地方的变化会导致其它的多个地方也必须随之变化。如果假定S为系统本身,M为对系统本身的一个测量,C为系统S中模块的平均复制份数(C>1),则这个M与C的关系应该是一个指数的关系: M正比于C的N次方(N>1)。
指数关系已经很可怕了,更可怕的是,当系统中的模块出现变化时,如果该模块在系统中有多个副本,我们可能偷懒,只改变了其中的一个副本,而不是全部副本都进行修改,这样就导致模块的分裂,由一个模块分裂成几个类似而又不同的模块,大大的增加系统的复杂度,最终导致系统的腐烂。直觉上,一个设计很烂的系统,它的复杂度大致是模块数量的阶乘关系甚至是幂指关系,这是比指数关系更恐怖的关系。
所以,复制和粘帖是一种非常邪恶的编码方式。在编码时,需要千方百计的去想办法减少复制和粘帖。这是在编码时就应该注意的问题,而不是放在重构阶段去做的事情。至于使用什么方法,使用什么手段,使用什么模式则是细节问题。
坚持不复制和粘帖,坚持下来,收益会非常大,写出来的代码质量高、含金量高。看见别人的系统,能马上分辨出这个系统的优点是什么,缺点是什么。什么设计模式也好,接口的正交性也好,设计原则也好,也许你从没刻意的去学过,却最终发现殊途同归,冥冥之中与国外大牛有一种心意相通的感觉。会自发的去组合、去改良这些大牛们的思想和方法,甚至去创造新方法新手段。直接由一入手,一生二,二生三生四,而非教条的、顶礼膜拜的去学这个三,学这个四。或许那个时候,你已经忘记什么是对象了。
之所以发这些牢骚,是因为昨天至今天,正在重构一个模块。这个模块M1的核心部件是一个包装自RTF的layout规则编辑器。设计这个核心部件的哥们以RichTextBox为中心设计了一个控件A,然后将这个控件的部分规则逻辑抽出来放在类B和类C的静态方法之中,更神奇的是这个类B是在另一个模块M2之中,类C倒是在模块M1之中。这个控件在M1中被三个地方给用到:D、E、F,这D、E、F每个地方都要为这个空间A注册七八个事件,然后在事件的回调函数中调用模块M2中的类B的静态方法及模块M1中的类C的静态方法去实现一些逻辑。现在呢,我要写一个控件G,这个G也要用到控件A,在这种情况下,我必需为G注册一堆A的事件及回调函数,然后在回调函数中弄一堆逻辑,至少得200行代码。为了写这些回调函数,我必须得搞清这个A控件及类B,类C的内部运行机制。也就是说,为了吃猪肉必须得亲自去杀猪。当然,也可以从D、E或F 中Copy代码过来改吧改吧来节省时间。
问题严重的地方在于,这个控件A本身存在逻辑错误,存在功能不完善的地方,需要对它动手术。因为到处复制,牵一发而动全身,给A动手术必须也要给B、C、D、E、F五个类动手术。在给A动手术时,为了编译通过,我将B、C、D、E、F中与A相关的代码全给注释掉了,前后注释了1500行代码左右。实质上这1500行代码真正有价值的代码也就在200行左右,其它的代码全是复制、粘帖,然后改改变量名完成的。
为什么会出现这样的问题呢?因为复制和粘帖。复制和粘帖省事啊,Copy过去改几个词就能用了,不用花费心思的去想封装。而实际情况是,要引用那个控件A,得写200-300行代码,多引用几处,就得写1000多行代码,复制和粘帖的话倒不费事,但如果发现这个A存在错误,或者需要扩展,在改A的同时,同时也要动这1000多行代码,这1000多行代码中可能会牵扯到更多的代码,最终导致必须修改更多的代码,这便是代码的腐烂。
其实这个A是很好封装的,它不需要其它的类对它输入任何输入数据,其它的类只需要从A控件中获得一个最终的规则结果,一个List。封装的好的话,调用A,获得结果,两三句代码就可以实现。
之所以不封装是因为习惯了复制和粘帖,或者懒于去封装,或者头脑中根本没封装这根弦。
很多新程序员或者不新的程序员,尤其是Web开发程序员老抱怨工作的技术含量低,老是想学更多的东西。实质上,他们所作的工作是非常有技术含量的东西,就看怎么看待。
如果只将自己的工作看作简单的复制、粘帖、抄袭、改代码的话,自然技术含量低了。如果将自己的工作看作如何消除复制和粘帖、如何提高质量、进度,消除工作中的不必要事情,消除各种浪费,那么这个工作的技术含量是极其高的。不要膜拜大师,当你这么做的时候,你做的正是大师的工作。不要膜拜新技术,当你这么做的时候,你的工作可能正是新新一代技术的萌芽。一点一滴、一色一香,全在心中。青青翠竹、尽是法身,郁郁黄花、无非般若。

编码的邪恶:复制与粘帖相关推荐

  1. 我的特长是复制、粘帖

    来自:大叔爱吐槽(id:dashuaitucao) 特长 大家好,我是工作时长两年半的程序员汤姆,喜欢谷歌.复制.粘帖和提交. 招聘 应聘程序员,HR一上来就问我:有对象吗? 我:分了! HR:为什么 ...

  2. vi 常用复制与粘帖技巧

    vi 常用复制与粘帖技巧 复制和粘贴是文本编辑中的常用操作,Vi也提供了这种功能. 复制是把指定内容复制到内存的一块缓冲区中,而粘贴是把缓冲区中的内容粘贴到光标所在位置. 复制和粘贴的方法如下. yw ...

  3. python复制word到粘贴板_python3+PyQt5实现使用剪贴板做复制与粘帖示例

    本文是对<Python Qt GUI快速编程>的第10章的例子剪贴板用Python3+PyQt5进行改写,分别对文本,图片和html文本的复制与粘帖,三种做法大同小异. #!/usr/bi ...

  4. 复制 和 粘帖 的方法(特别在linux中),备忘

    终端(Terminal)下,一般是Ctrl-Shift-c /Ctrl-Shift-v . 控制台下,鼠标选中就是复制了,Shift-Insert粘贴 粘贴用Shift-Insert,通用. 图形界面 ...

  5. VIM 中复制和粘帖

    本文转自:http://blog.csdn.net/zhengxinjian_2009/article/details/7846407 在vi编辑器有一个寄存器的概念(concept of regis ...

  6. Linux Vim 光标错位,技术|Vim 复制粘帖格式错乱问题的解决办法

    有时候,复制文本(尤其是代码)到 Vim,会出现格式错乱的问题.看样子,应该是自动缩进惹得祸.本文不去深究原因,直接给出解决方法. 1. paste 模式 运行如下命令,进入 paste 模式: :s ...

  7. vim与外部文件的粘帖复制

    vim与外部文件的粘帖复制 ubuntu默认vim是不支持从外部文件与vim之间的粘帖复制,vim有自己的剪切版,分别是"0-"9,"-,"8,"+, ...

  8. C# 在word文档中复制表格并粘帖到下一页中

    C# 在word文档中复制表格并粘帖到下一页中 object oMissing = System.Reflection.Missing.Value;             Microsoft.Off ...

  9. 微信拜年信息“大爆发”,真挚的祝福只剩下粘帖与群发

    很多人都有这样的感觉:一到春节,手机信息提示音就响个不停,祝福信息一个接一个,心里开心的同时,也为内容重复的群发信息而苦恼.马上就是春节了,正是微信拜年信息"大爆发"的日子,许多朋 ...

最新文章

  1. phalcon遇到的那些坑
  2. BZOJ2091 [Poi2010]The Minima Game
  3. HTML框架IFrame结合JS在主页面和子页面间传值
  4. 静态链接库与动态链接库
  5. react 16.6 懒加载 Lazy 尝鲜
  6. java 设置文本颜色_设置文本中的字体的颜色
  7. 《大数据、小数据、无数据:网络世界的数据学术》一 3.5 交流融合
  8. CUDA和LAPACK混编的MakeFile文件
  9. 浏览器原理学习笔记1-浏览器进程
  10. iSlide系列教程视频简介——PPT的简化神器
  11. IP模拟工具modify header
  12. Codeforces407C Curious Array
  13. 2021总结2022规划
  14. opencv之图像平移
  15. 组织病理学的生存模型综述
  16. 第二十二届全国青少年信息学奥林匹克联赛初赛
  17. Spotify网络钓鱼活动目标锁定音乐爱好者
  18. 简单几步骤,裁剪多个视频画面大小
  19. Linux中级(六)Proxy服务器
  20. Linux部署ElasticSearch搜索引擎步骤

热门文章

  1. 识别视频声音内容添加字幕
  2. 2005年1月7日0:34:06
  3. Revitalizing CNN Attentions via Transformers in Self-Supervised Visual Representation Learning
  4. 解读:电子合同、电子签名、电子印章、数字认证之间的关系
  5. poi中Numeric的理解
  6. Java语言学习笔记——20121221课程笔记
  7. 软考证书对找工作有没有帮助?肺腑之言
  8. Python正则化匹配读取txt数据转为list列表
  9. python 通达信k线_[python]沪深龙虎榜数据导入通达信的自选板块,并标注于K线图上...
  10. SAA-C02学习记