【发布时间】:2010-05-03 13:47:38
【问题描述】:
我想创建一组具有许多共同行为的类。当然,在 OOP 中,当您认为您会自动想到“带有子类的抽象类”时。但是我希望这些类做的事情之一是每个类都有一个静态的类实例列表。该列表应该作为类中的单例。我的意思是每个子类都有一个单例,而不是它们共享一个。该子类的“单例”,而不是真正的单例。但是如果是静态的,我怎么继承呢?
当然这样的代码是行不通的:
public abstract A
{
static List<A> myList;
public static List getList()
{
if (myList==null)
myList=new ArrayList<A>(10);
return myList;
}
public static A getSomethingFromList()
{
List listInstance=getList();
... do stuff with list ...
}
public int getSomethingFromA()
{
... regular code acting against current instance ...
}
}
public class A1 extends A
{
...
}
public class A2 extends A
{
...
}
A1 somethingfromA1List=(A1) A1.getSomethingFromList();
A2 somethingfromA2List=(A2) A2.getSomethingFromList();
每个子类的列表内容会有所不同,但在列表上工作的所有代码都是相同的。
上述代码的问题在于,我只有一个包含所有子类的列表,并且我想要每个子类一个。是的,我可以复制代码以在每个子类中声明静态列表,但是我还必须复制添加到列表和搜索列表等的所有代码,这反而违背了子类化的目的。
关于如何在不复制代码的情况下做到这一点的任何想法?
更新
为了向 BlueRaja 和其他人澄清,让我更具体地说明我正在尝试做什么。
我有许多需要类似行为的状态和代码。它们就像枚举,因为我希望为每种可能的代码状态提供类型安全的实例,但它们有多个集合,所以我不能只为它们创建一个枚举。
例如,我有订单状态,其中包含在订单、已发货、已收到的值和一些特殊值。我有项目类型,具有商品与服务的值。我有库存与定制。等等。
如果这就是它的全部,我会为每一个做一个枚举。但是我还需要其他行为,例如通过文本值查找对象的能力,例如当我们从数据库中读取它时;建立一个下拉列表,通过文本描述列出所有选项;等等。据我所知,我不能用枚举来做到这一点,因为我有几组代码,每组都有我想要继承的共同行为,而且我不能子类化枚举。将所有代码放在一个枚举中会放弃一个代码与另一个代码的类型安全性,并证明没有现成的方法来收集特定代码类型的值列表。
【问题讨论】:
-
不要在面向对象的世界中使用静态保持状态,这是错误的。
-
不要使用单例,对静态数据要非常小心。更喜欢组合而不是继承。真的,你提到的几乎没有什么是真正“好的 OOP”。
-
好的。所以我有一组给定子类的实例,我需要维护所有这些实例的列表,用于搜索、构建下拉列表等。好吧,我可以创建一个包含该列表的(非静态)对象。但只有一个列表才有意义。那么这样做有什么好处呢?如果我创建了两个具有不同列表的对象,那就大错特错了。如果没有单例,你将如何解决问题?
标签: java design-patterns oop singleton