《Clean Code》学习之—Objectes and Data Structures

        在这一章中,bob大叔对对象和数据结构所要遵循的规则进行了阐述。下面我们来看看他主要讲了些什么。

        Data Structure(数据抽象)

        我们不要暴露数据内部的详细情况,而是要用抽象的方式来表示数据。这一段实际上说的比较乱,中心意思应该是要注意数据的抽象性,不要用太多的setters和getters将数据暴露出来。

        Data/Object Anti-Symmtry(反对称性)

        对象一般将数据隐藏再抽象化的背后,而将运行在这些数据上的方法暴露出来;数据结构会暴露内部的数据但不会带有什么有意义的函数。

        下面是一块面向过程的代码:

        public class Square{

          public Point topleft;

          public double side;

        }

        public class Rectangle{

          public Point topLeft;

          public double height;

          public double width;

        }

        public class Geometry{

          public final double PI = 3.141592653589793;

          public double area(Object shape) throws NoSuchShapeException

          {

            if (Shape instanceof Square){

              Square s = (Square)shape;

              return s.side * s.side;

            }

            else if (shape instanceof Rectangle){

              Rectangle r = (Rectangle)shape;

              return r.height * r.width;

            }

            else if (shape instanceof Circle){

              Circle c = (Circle)shape;

              return PI * c.radius * c.radius;

            }

            throw new NoSuchShapeException();

          }

        }

            对于上面一段代码,如果往Geometry中加入一个函数perimeter()的话,那么所有的shape类都不受影响,并且所有其它基于shapes的方法都不受影响。但是另一方面,如果新增了一个shape, 那么我们需要修改Geometry中所有处理shapes的函数。

           再看看下面的代码:

public class Square implements Shape{
  private Point topLeft;
    private double side;
    public double area(){
      return side * side;
  } 
}

public class Rectangle implements Shape{
    private Point topLeft;
    private double height;
    private double width;
    public double area(){
      return height * width;
  } 
}

public class Circle implements Shape{
   private Point center;
  private double radius;
  public final double PI = 3.141592653589793;
  public double area(){
    return PI * radius radius;
  }
}

        从上面的代码可以看出,这是面向对象的代码。其中area()函数使用的就是多态的技术。如果加进来一个新的shape,所有现存的函数都不会受到影响,但是如果我加入一个新的函数,所有的shapes都要改变。

        从上面的比较中可以发现面向过程的代码(使用数据结构)和面向对象的代码各有优缺点。面向过程的代码易于加入新的函数而无需改变现存的数据结构;面向对象的代码易于增加新的类而无需改变现存的函数。

The Law of Demeter(迪米特法则)

        迪米特法则又叫最少知识原则,就是说一个对象应该对其他对象内部细节尽可能少的了解。

        迪米特法则需要遵守如下原则:类C中的模块f只能调用如下几种方法:

        (1)C中的方法

        (2)f所创建的对象的方法

        (3)传递给f的作为参数的对象的方法

        (4)C的实例所持有的对象的方法

        f不要调用上面这些方法所返回的对象中的方法,换言之:可以和朋友说话,但不要跟陌生人说话。

        TrainWrecks(火车失事)

         下面这样的代码常常被称为火车失事:

        final String outputDir = ctxt.getOptions().getScratchDir().getAbsolutePath();

        我们常常要把它们打散成如下的形式:

        Options  opts = ctxt.getOptions();

        File scratchDir = opts.getScratchDir();

        final String outputDir = scratchDir.getAbsolutePath();

        后面还有一丁点的内容,先不管了吧,很晚了,早点回家,呵呵。

posted @ 2011-10-27 22:11  Core Hua  阅读(327)  评论(0)    收藏  举报