面向对象的编程架构与数据库访问设计

问题描述 投票:0回答:1

考虑到面向对象编程,数据库如何与对象一起发挥作用?例如,假设有一个 Student 类,具有姓名、编号、课程等属性

Student类也有行为(方法)。我认为合适的一些是

enrollForACourse()
dropACourse()
getStudentGPA()
getAllStudentCourses()
等,或类似的东西。我不确定这些示例方法在凝聚力方面是否良好,但我会说是或也许。

我需要帮助的是数据库部分。因此,如果另一个不同的对象、用户或其他东西想要了解学生拥有的课程,则将使用 Student 类上的 getAllStudentCourses 方法。但不可避免的是,该信息存储在数据库中。

那么学生班级的

getAllStudentCourses()
方法会向数据库查询此信息吗?这是好的做法吗?这会遵循面向对象设计吗?等等同样适用于
enrollForACourse()

如果 Student 类需要在方法中查询外部第 3 方服务怎么办?

oop design-patterns architecture object-oriented-analysis
1个回答
0
投票

你的问题不够明确和具体。但我指出一些注释来帮助你。与数据库进行通信建模有很多因素。

  • ORM:对象关系映射是一种在关系数据库和程序中的对象之间转换数据的技术。 ORM 在细节上有所不同,但它们做同样的事情:获取实体并将其转换为指定的对象。并对实体进行 CRUD 操作。例如,Django ORM(Python 中)使用活动记录模式。实体负责提交其变更。但在实体框架 (.NET c#) 中,实体不知道数据库连接以及如何提交更改。包装容器 (DbContext) 完成这项工作。这样,您就可以应用工作单元模式。
  • 应用程序架构:您的应用程序可以使用许多架构,这些架构会影响您检索和修改数据的方式。例如,CQRS 架构模式使您可以使用单独的模型来读取和写入数据。
  • 设计模式:一些设计模式说明了如何使用数据。存储库和工作单元模式是最重要的。存储库模式指出您应该定义一个像内存中集合一样工作的接口。如果您有一个 User 表,您应该有一个代表该表的接口 IUserRepository。它包括客户需要的所有必需方法,例如 CRUD。工作单元可帮助您在一个事务中提交所有更改,或者在出现任何问题时回滚所有更改。

关于您的示例,其中一些会修改数据的状态,我们将其称为命令。命令可以在实体对象中具有相应的行为(实际上是方法)。

enrollForACourse
dropACourse()
是命令示例。但对于
getStudentGPA()
getAllStudentCourses()
,它们是其他对象(如存储库或(CQRS 中的查询处理程序))负责的查询。不要将您的查询放在实体本身中。查询很复杂,您的实体不应该被这些复杂性所污染。

GRASP 原则试图将职责分配给班级。所有这些技术、模式和实践都是为了遵守 GRASP。所以从面向对象的角度来看,你不应该在实体中放置额外的职责。

我不确定这些示例方法在凝聚力方面是否良好,但我会说是或也许。

我说这要看情况。其中一些很简单,可以通过导航属性(反映两个表之间关系的属性)来处理,就像您的所有四个示例一样,其中一些是复杂的查询或命令,涉及多个实体来处理(如

CanStudentEnrollInACourse()
)。在这些情况下,您应该使用存储库或查询处理程序。因为责任不在实体的范围内。

学生班级的 getAllStudentCourses() 方法会创建一个 查询数据库以获取此信息?这是好的做法吗?并且会 这遵循面向对象设计吗?等等与 enrollForACourse() 相同。

是的,只要实现不包含任何数据访问逻辑,例如导航属性(ORM 必须支持此功能),就可以接受。

如果 Student 类需要在方法中查询外部第 3 方服务怎么办?

为什么需要查询其他服务?是否可以将结果传递给实体?如果没有,您可以将第三方服务接口传递给您的实体。你的实体不会是纯粹的,但这样责任会更清晰。

© www.soinside.com 2019 - 2024. All rights reserved.