我不确定这两种“模式”中哪一种最好。目前我使用选项A(与提供程序一起实现持久性),但我现在正在向B做错,特别是考虑到单元测试能够使用“依赖注入”模型。
选项A:
class ClassA
{
ClassA() { }
Save();
static List<ClassA> GetClassAs();
}
选项B:
class ClassA
{
ClassA() { }
Save();
}
class ClassARepository
{
ClassARepository() { }
List<ClassA> GetClassAs();
}
我认为我要问的是,一个类暴露返回自身实例集合的静态方法是不错的做法?
似乎普遍认为选项B是更好的选择。看起来我前面有很多重构:S
答案 0 :(得分:4)
选项B看起来有点像ActiveRecord模式(我假设ClassA中的Save方法将使用ClassARepository?),这在某些情况下很好,但是,如果你有相当复杂的域模型,我不会使用'ActiveREcord'模式。
相反,我会使用这样的模型:
public class ClassA
{
public int Id {get; private set;}
public string Name {get; set;}
}
public class ClassARepository
{
public ClassA Get( int id );
public void Save( ClassA item );
}
这意味着所有与持久性相关的逻辑都放在ClassARepository类中,而ClassA也没有直接访问存储库。
答案 1 :(得分:2)
您可以将对象的完全持久性与数据和逻辑分开,也可以将所有对象保留在一个类中。将“保存”移至“ClassARepository”或将“GetClassAs”保留在“ClassA”中。
答案 2 :(得分:1)
选项B看起来更好,因为A混合了两种想法,两种功能。有A类的实际功能和管理A的集合的单独功能。
随着应用程序的增长,您可能还需要在存储库中使用其他功能 - findById,检索子集等等。把它变成A级会变得混乱。
而且,正如您所指出的,选项B更容易测试。
答案 3 :(得分:0)
不,我不认为这种不良做法是一项严格的规则,尽管我假设这是针对某种实例跟踪或资源监控的吗?如果是这样,请记住,幕后必须有逻辑,以确保原本超出范围的对象不会仅仅停留在静态集合中。我不确定您使用的是哪种语言,但如果是C#,您可以考虑将其作为List<WeakReference>
内部存储。
答案 4 :(得分:0)
选项B更灵活。
答案 5 :(得分:0)
我认为我要问的是,一个类暴露返回自身实例集合的静态方法是不错的做法?
一般情况下没有 - 这样的收藏品通常是单身人士,如果是(如你的例子)那么单身人士的常见原因被认为是antipattern,以及static is considered harmful的原因。 / p>