• 2012-05-20

    代码之丑(十一)

    版权声明:转载时请以超链接形式标明文章原始出处和作者信息及本声明
    http://www.blogbus.com/dreamhead-logs/214225975.html

    全局变量永远是不受欢迎的,因为它会带来太多的问题,所以,诸如Java这样的程序设计语言干脆摒弃了全局变量。一旦我们有机会面对全局变量,想都不要想,干掉它。

    if (IDLE == g_status) {
      ...
    }

    那个g打头的家伙就是全局变量,它就是我们的靶子。第一直觉,我们不要直接访问全局变量,那就用函数把它封装起来:

    int getCurrentStatus() {
      return gStatus;
    }

    于是,代码变身了:

    if (getCurrentStatus() == IDLE) {
      ...
    }

    把变量封装成函数,从某种角度说,这是一种进步。但我想说,这还不够。这只是一种简单的封装,本质上来说,这与直接暴露数据差别不大,我们需要更好的封装,通常的做法是封装出行为。行为从哪来,从实际需求来。

    就以上面这段代码为例,我们封装了status,其实,它的目的是为了与IDLE状态相比较,这就是一种行为,我们可以这样封装:

    bool isCurrentStatus(int status) {
      return status == g_status;
    }

    if (isCurrentStatus(IDLE)) {
      ...
    }

    还有一种修改方式,既然IDLE是一个固定的常量,索性把它也隐藏起来:

    bool isIdle() {
      return IDLE == g_status;
    }

    if (isIdle()) {
      ...
    }

    实际上,这种封装出行为的方式不仅仅适用于全局变量,把数据拿出来再用的情形也是经常可以见到的:

    if (machine.getStatus() == IDLE) {
      ...
    }

    封装的方式同上面一样,这里选择一种实现:

    class Machine {
      ...
      bool isIdle() {
      return status == IDLE;
      }
    }

    if (machine.isIdle()) {
      ...
    }

    封装,就得封装出个行为来。


    本文已经首发于InfoQ中文站 ,版权所有,原文为《专栏:代码之丑(十一)》,如需转载,请务必附带本声明,谢谢。

    InfoQ中文站是一个面向中高端技术人员的在线独立社区,为Java、.NET、Ruby、SOA、敏捷、架构等领域提供及时而有深度的资讯、高端技术大会如QCon 、免费迷你书下载如《架构师》等。

    分享到:
    引用地址:

    评论

  • 仅作为理论的学习。最好能补充上下文,不然不足描述此封装带来的价值。
    作为实践而言,是否有必要使用封装,也值得探讨。
    正如建筑学是一门严谨的学术,但是用于建筑高楼大厦的实践,和用于搭建一个狗窝的实践方法,显然是大相径庭的。
    回复stone2083说:
    这个建议不错,但是作为如此长度一篇blog,恐怕也很难尽述。这里所描述的技术不是架构层面的,更多是编码级别,几乎可以原封不动在自己的代码中,照方抓药。有什么更多的想法,欢迎留言。
    2012-05-28 21:52:13