我们知道,在面向对象设计中要做到高内聚低耦合。而单一职责原则就是实现高内聚低耦合的最好办法。面向对象设计中单一职责原则是指:
一个类只负责一个功能领域中的相应职责。
如果一个类承担的职责过多,就等于把这些职责耦合在了一起。当其中一个职责变化时,可能影响其他职责的运作。
下面我们用C++的例子来具体说明。
比如我们有如下的设计:
class CShape
{
public:
virtual ~CShape();
virtual void Draw() = 0;
virtual double GetArea() = 0;
};
class CSquare : public CShape
{
public:
void Draw();
double GetArea();
void SetWidth(double dWidth);
double GetWidth();
private:
double m_dWidth;
};
现在有两个不同的应用程序用到了类CSquare,一个是有关几何计算方面的,另一个是有关图形方面的。对于前者而说,程序从来不需要绘制图形;而对于后者来说,程序也从来不需要计算图形的面积。
在上面这种情况下,我们的设计就违反了单一职责原则。它即提供了几何计算方面的功能,又提供了图形绘制方面的功能。这样,在有关几何计算方面的应用程序中就要链接图形显示方面的库文件;而在有关图形方面的应用程序中却链接了数学计算方面的库文件。而这些多余的链接其实是不必要的。它们不但会使编译、链接的时间变长,而且会使应用程序占用的内存增加。如果我们对图形的显示代码做了修改,那么有关几何计算方面的应用程序就要重新链接。我们为什么要为自己不需要的功能重新链接自己的程序呢?因此,上面的设计是不正确的。
下面是一个符合单一职责原则的设计。在这个设计中,把原来的类CShape分为两个类:CGeometricShape和CGraphicalShape,来分别承担几何和图形两方面的职责。同样,分别派生出GGeometricSquare和CGraphicalSquare。
class CGeometricShape
{
public:
virtual ~CGeometricShape();
virtual double GetArea() = 0;
};
class GGeometricSquare : public CGeometricShape
{
public:
double GetArea();
void SetWidth(double dWidth);
double GetWidth();
private:
double m_dWidth;
};
class CGraphicalShape
{
public:
virtual ~CGraphicalShape();
virtual void Draw() = 0;
};
class CGraphicalSquare : public CGraphicalShape
{
public:
void Draw();
void SetWidth(double dWidth);
double GetWidth();
private:
double m_dWidth;
};
这样,有关几何计算方面的应用程序和有关图形方面的应用程序之间就没有一点儿耦合了。不仅应用程序中不会链接多余的代码,而且对其中的任意一个类进行修改都不会影响到另外一个应用程序。