当我设计我的类时,我正在努力解决循环依赖的问题。
自从我读到Anemic Domain Model (我一直在做的事情)以来,我真的一直在努力摆脱创建域对象,这些对象只是“大量的getter和setter”,并返回到我的OO根。
然而,下面的问题是我经常遇到的问题,我不确定我应该如何解决它。
假设我们有一个Team类,它有许多Player。这是什么运动并不重要:)一个团队可以添加和删除球员,就像一个球员可以离开一个团队加入另一个团队一样。
所以我们有一个团队,它有一个球员列表:
public class Team {
private List<Player> players;
// snip.
public void removePlayer(Player player) {
players.remove(player);
// Do other admin work when a player leaves
}
}
然后是Player,它引用了球队:
public class Player {
private Team team;
public void leaveTeam() {
team = null;
// Do some more player stuff...
}
}
可以假设这两个方法(remove和leave)都有特定于域的逻辑,每当球队移除球员和球员离开球队时,都需要运行该逻辑。因此,我的第一个想法是,当Team踢到一个球员时,removePlayer(...)还应该调用player.leaveTeam()方法...
但是,如果播放器驱动了变化- leaveTeam()方法是否应该调用team.removePlayer(this)呢?如果不创建无限循环,就不会!
在过去的中,我只是让这些对象成为“哑巴”POJO,并让一个服务层来做这项工作。但即使是现在,我仍然面临这个问题:为了避免循环依赖,服务层仍然将所有这些都链接在一起--即
public class SomeService {
public void leave(Player player, Team team) {
team.removePlayer(player);
player.leaveTeam();
}
}
我是不是把事情搞得太复杂了?也许我遗漏了一些明显的设计缺陷。任何反馈都将非常感谢。
感谢所有人的回复。我接受Grodriguez's解决方案,因为它是最明显的(不敢相信我没有想到)并且易于实现。然而,DecaniBass确实提出了一个很好的观点。在我描述的情况下,一个球员有可能离开一个团队(并知道他是否在一个团队中)以及驱动移除的团队。但我同意你的观点,我不喜欢这个过程中有两个“入口点”的想法。再次谢谢。
发布于 2010-10-24 15:52:38
您可以通过添加后卫来检查球队是否仍有球员/球员是否仍在球队中,从而打破循环依赖。例如:
在类Team
中
public void removePlayer(Player player) {
if (players.contains(player))
{
players.remove(player);
player.leaveTeam();
// Do other admin work when a player leaves
}
}
在类Player
中
public void leaveTeam() {
if (team != null)
{
team.removePlayer(this);
team = null;
// Do some more player stuff..
}
}
发布于 2010-10-24 16:15:52
本,
首先,我会问一个球员是否可以(逻辑上,合法地)将自己从球队中剔除。我想说球员对象不知道他在哪支球队(!),他是球队的一部分。因此,删除Player#leaveTeam()
并通过Team#removePlayer()
方法进行所有团队更改。
如果您只有一个球员,并且需要将其从其团队中删除,那么您可以在team public static Team findTeam( Player player ) ...
上使用静态查找方法
我知道这不如Player#leaveTeam()
方法令人满意和自然,但根据我的经验,您仍然可以拥有一个有意义的域模型。
双向引用(父->子和子->父)通常充满了其他东西,比如垃圾回收、维护“引用完整性”等。
设计是一种妥协!
发布于 2010-10-24 16:03:18
我的想法是在不同的方法中做领域相关的事情,这些方法彼此不调用,但为他们自己的对象做领域相关的事情,即团队的方法为团队做,球员的方法为球员做
public class Team {
private List<Player> players;
public void removePlayer(Player player) {
removePlayerFromTeam(player);
player.removeFromTeam();
}
public void removePlayerFromTeam(Player player) {
players.remove(player);
//domain stuff
}
}
public class Player {
private Team team;
public void removeFromTeam() {
team = null;
//domain stuff
}
public void leaveTeam() {
team.removePlayerFromTeam(this);
removeFromTeam();
}
}
https://stackoverflow.com/questions/4007451
复制相似问题