我更好地解释用一个例子的问题。 我具有可以被用来访问数据的接口模型 。 可以有模型的不同实现可以表示各种格式的数据说XML,txt格式等模型不涉及格式。 比方说,一个这样的实现方式是myxmlModel。
现在我想迫使myxmlModel和所有其他的实现模型遵循Singleton模式 .The通常的方法是使myxmlModels构造私人和提供静态工厂方法返回基于myModel class.But实例的问题是接口不能有静态方法定义并因此我无法对模型的所有执行实施特定的工厂方法定义。 所以,一个实现可以与提供的getObject()结束等可能有newModel,并向获得()。 。
一个解决办法是允许myxmlModel的构造函数包访问,并创建创建myxmlModel对象工厂类,并将它缓存为进一步使用。
我不知道是否有更好的方法来实现相同的功能。
- 做一个工厂,返回你的接口,模型的实例。
- 请在同一个包作为您的工厂模型包私有类的所有具体实现。
- 如果您的模型是一个单身,你正在使用Java 5+,用枚举,而不是传统的单,因为它是更安全的。
public enum MyXMLModel{
INSTANCE();
//rest of class
};
编辑:另一种可能性是创建委托类,做所有的工作,然后使用一个枚举提供所有型号选项。
例如:
class MyXMLModelDelegate implements Model {
public void foo() { /*does foo*/}
...
}
class MyJSONModelDelegate implements Model {
public void foo() { /*does foo*/ }
...
}
public enum Models {
XML(new MyXMLModelDelgate()),
JSON(new MyJSONModelDelegate());
private Model delegate;
public Models(Model delegate) { this.delegate=delegate; }
public void foo() { delegate.foo(); }
}
您可以使用反射。 事情是这样的:
public interface Model {
class Singleton {
public static Model instance(Class<? extends Model> modelClass) {
try {
return (Model)modelClass.getField("instance").get(null);
} catch (blah-blah) {
blah-blah
}
}
}
public class XmlModel implements Model {
private static final Model instance = new XmlModel();
private XmlModel() {
}
}
用法:
Model.Singleton.instance(XmlModel.class)
其实,我不喜欢这样的代码更:)。 首先,它使用反射 - 很慢,第二 - 有在类错误定义的情况下运行时错误的可能性。
你可以重构接口是一个抽象类? 这将允许您强制一个特定的工厂方法到所有的实现类。
我常常问自己同样的问题。 我提出了同样的答案;-)
现在,我通常删除“强制”的行为,我靠的文档。 我没有发现任何情况下辛格尔顿方面是如此引人注目,它需要通过各种手段来实施。 这只是一个“最佳实践”的项目。
我通常使用Spring来实例化这样的对象,并且它是弹簧结构,使得它一个Singleton。 安全,很容易...加上其它附加春优势(如代理功能,substituing不同的对象,一旦做一些测试,等...)
这更多的是一个答案,你的意见/澄清KTS的答案。 是这样吗,真正的问题不是使用Singleton模式,而是定义蚀(春分)扩展点的架构,允许贡献了单?
我认为,这不能做,因为每次你打电话IConfigurationElement.createExecutableExtension您创建一个新的实例。 这是你的单身的要求格格不入。 因此,你需要的公共默认构造函数,这样每个人都可以创建实例。
除非你可以改变扩展点定义,以便插件贡献ModelFactory,而不是一个模型,如
public interface ModelFactory {
public Model getModelInstance();
}
所以,分机用户将实例化一个ModelFactory,并用它来获得单。
如果我猜错了,发表评论,我删除了答案;)