在应用接口隔离时,是否应该为简单的设置器和在设置前执行操作的接口提供单独的接口?例如,假设您有一个类:
class FooClass:
public GettableFoo,
public SettableFoo
{
virtual int getRelevantData();
// member of GettableFoo (which is used by roughly 20 clients)
virtual void setToOtherFooTemplate(GettableFoo *other);
// member of SettableFoo (which is used by roughly 20 clients, some of which also need GettableFoo interface)
void setToSum(GettableFoo *a,GettableFoo *b);
// requires SettableFoo functions to implement, used by 8 clients, some of which also need SettableFoo interface
void combineSomeOtherWay(GettableFoo *a,GettableFoo *b);
// requires SettableFoo functions to implement, used by 4 clients (possibly more in the future), some of which also need SettableFoo interface and/or which require the setToSum function
private:
// complex data
}接口隔离原则规定,任何客户端都不应被迫依赖它不使用的方法。这是否意味着setToSum()和combineSomeOtherWay()都应该有自己的接口?答案似乎应该是肯定的,但我想我从来没有见过有那么多接口隔离的代码。
如果上面的答案是肯定的,那么这不意味着如果combineSomeOtherWay()只是setToProduct() (乘),并且我使用操作符重载来在C++中实现这一点,那么从技术上讲,考虑到客户端的需要,操作符重载将破坏接口隔离原则吗?如果是这样的话,大多数使用操作符重载的情况都会破坏ISP吗?如果没有,这与没有隔离上述类中的任何接口有什么不同?
发布于 2015-07-27 18:31:22
我建议您从客户端代码的角度来看ISP。
你的班级在几个地方被使用?是否有任何客户机类只需要一种方法,而不需要另一种方法?如果所有客户端代码都需要这两个接口,那么两个接口的情况似乎就不存在了。
如果您确实有两个不同的地方使用您的类,每一个都需要一种方法,而不是另一种方法,接口隔离原则认为您应该为每个用例提供一个接口。然后,类将显式实现两个接口。
请记住,在经常被引用的“施乐”故事中,ISP的发明是分解上帝物体的第一步。为类拥有两个接口是可以的,但是值得问问自己,这个类是否可以被分成两半。正如其他人所说,ISP与SRP (单责任原则)之间有着密切的联系。
发布于 2015-09-04 16:15:20
我发现将接口看作对象可以扮演的角色是很有帮助的。因此,如果客户端依赖于一个角色来完成它的工作,那么它将只依赖于一个接口。
如果一组方法属于同一个角色,那么将它们放在一个接口中并不违反ISP。例如,一组用于以稍微不同的方式执行同一件事情的互斥重载可能属于单个角色。
隔离接口是一件好事,因为它赋予了客户能力,并鼓励他们以更模块化的方式设计,并与更窄的合同相结合。与OOP的其他一些技术/模式不同,它并不会导致重大的过度工程或其他开销。
如果有意义的话,您总是可以轻松地将多个接口合并回一个接口。更难的是,在您已经有了一群客户端之后,因为它们可以依赖一个巨大的接口,所以很难拆分它们,这些客户端现在有太多的责任和耦合。这就是为什么依赖客户端来告诉您如何分割接口并不总是一个好主意。
摘要:
https://softwareengineering.stackexchange.com/questions/287458
复制相似问题