为什么在Dao设计模式或其他设计模式中使用接口

时间:2014-05-09 10:10:24

标签: java spring hibernate design-patterns

请参阅以下Dao设计模式的组件:

数据访问对象模式或DAO模式用于将低级数据访问API或操作与高级业务服务分开。以下是数据访问对象模式的参与者。

数据访问对象接口 - 此接口定义要对模型对象执行的标准操作。

数据访问对象具体类 - 该类实现上面的接口。该类负责从数据源获取数据,该数据源可以是database / xml或任何其他存储机制。

模型对象或值对象 - 此对象是包含get / set方法的简单POJO,用于存储使用DAO类检索的数据。

为什么我们有一个具体的课程时需要一个INTERFACE,为什么我们不能直接使用它?这可能是一个天真的问题,但请帮助我明确这一点。不仅在DAO设计模式中,在其他设计模式中,使用INTERFACE也有点令人困惑。我同意这与代码可重用性和减少耦合有关。但任何人都可以请进一步解释。

6 个答案:

答案 0 :(得分:23)

  

不仅在DAO设计模式中,而且在其他设计模式中也使用   INTERFACE有点令人困惑。

接口是Java中使用最好的概念之一。让我用一个例子解释一下:假设你为汽车设计了一个GPS设备,它可以看到地图并自动将汽车转向地图中所示的方向。这种GPS设备可用于许多汽车,如奔驰,菲亚特等。对于每辆汽车,左右转动的机制可能根据汽车系统的实施而有所不同。因此,这些功能应该由汽车制造商编写,因此这些方法被放置在一个界面中,该界面由汽车制造商根据其汽车的实施来实现。界面仅包括一组功能声明,这些功能将由汽车制造商(在本例中)定义。得到它了?

要详细了解界面及其有用的原因,请阅读this article

  

我的问题是:当我们有一个具体的时候,为什么我们需要一个接口   我们为什么不能直接使用它。

在下面的答案中指出的许多其他好处中,您可以为实现DAO接口的不同数据结构(derby db,large stacks等)创建许多DAO类。好处是,每个类都可以存储在DAO接口变量中,称为polymorphism

答案 1 :(得分:13)

实际上,当您只有一个实现时,没有必要拥有一个接口。但是在某种情况下,你不具备对具体课程的依赖是非常实际的:

  • 测试调用DAO的服务:您可以编写模拟DAO 在测试中就像你需要它一样(例如那里的模拟) 没有DB连接,很难自动重现)

  • 为你的DAO生成一些图层。您可以使用AOP生成 围绕DAO方法的缓存或事务处理。在这种情况下 你有一个实现DAO接口但没有任何东西的对象 与原始实施有关。

  • 切换数据库技术。如果你从MySQL切换到DB2,你就是 需要编写接口的另一个实现并切换 MySQL DAO和DB2 DAO

因此,为您提供DAO和服务接口是一种很好的做法。

答案 2 :(得分:7)

  

我的问题是,当我们有一个具体的课程时,为什么我们需要一个INTERFACE,为什么我们不能直接使用它。

这是简单的抽象。假设您使用Oracle数据库作为数据库。 因此具体类将具有访问(CRUD操作)Oracle DB的逻辑。明天,如果您的许可证到期并且您不再想使用Oracle DB,那么您将需要使用MySQL。现在你必须重写已经提到的具体类,并且你必须重写服务层,因为通过直接使用具体类和它的方法,你在服务层和数据访问层之间有紧密耦合。人们应该始终考虑松散耦合的系统。

如果您要使用接口而不是具体类,则服务层和数据访问层具有如何交互的契约。因此,服务层不会受到数据层更改的影响,因为合同没有改变,并且它们可以以相同的旧方式进行交互。

答案 3 :(得分:2)

将接口与实现分开始终是一个很好的设计。它为您的代码提供了更多抽象灵活性。 DAO接口的客户端不需要知道它是如何实现的,而只需要知道它提供的方法。

最后,接口是代码可维护性的一种很好的做法。

只是补充一下,根据我通过模拟测试单元测试的经验,当你模拟的对象有一个接口时,创建模拟对象要容易得多。因此,对我而言,使用接口可以更轻松地隔离测试您的代码。

答案 4 :(得分:0)

这更多地围绕着代码的逻辑分离。

有关接口的详细信息,请从Java阅读本页:

http://docs.oracle.com/javase/tutorial/java/concepts/interface.html

答案 5 :(得分:0)

一个很好的理由是,它可以轻松编写用于测试应用程序的模拟实现。

假设您要测试使用UserService的模块X.编写测试代码时,您希望它不使用真正的UserService,而是使用UserService的特殊测试版本来返回一些预定义的测试数据。因此,在您的测试中,您将传递自己的IUserService模拟实现,而不是真正的UserService。

此外,它使将来使用IUserService的不同实现扩展系统变得更加容易。也许你现在有一个UserService,它从数据库中读取有关用户的信息。例如,将来您可能还希望拥有一个从LDAP获取信息的UserService。那只是IUserService的另一个实现。由于应用程序的其余部分仅通过接口使用UserService,因此可以轻松地将一个实现替换为另一个实现。