关于膨胀的构造函数调用问题,您可以引入参数类或工厂方法来为您解决这个问题。
参数类将一些参数数据移动到它自己的类中,例如:
var parameterClass1 = new MenuParameter(menuBar, editor);
var parameterClass2 = new StuffParameters(sasquatch, ...);
var ctrl = new MyControllerClass(managedStore, parameterClass1, parameterClass2);
不过,它只是将问题转移到其他地方。您可能想要对您的构造函数进行管家处理。仅保留在构造/启动相关类时重要的参数,其余的使用 getter/setter 方法(如果您正在使用 .NET,则使用属性)。
工厂方法是一种创建您需要的类的所有实例并具有封装所述对象的创建的好处的方法。它们也很容易从 Singleton 重构,因为它们类似于您在 Singleton 模式中看到的 getInstance 方法。假设我们有以下非线程安全的简单单例示例:
// The Rather Unfortunate Singleton Class
public class SingletonStore {
private static SingletonStore _singleton
= new MyUnfortunateSingleton();
private SingletonStore() {
// Do some privatised constructing in here...
}
public static SingletonStore getInstance() {
return _singleton;
}
// Some methods and stuff to be down here
}
// Usage:
// var singleInstanceOfStore = SingletonStore.getInstance();
很容易将其重构为工厂方法。解决方案是删除静态引用:
public class StoreWithFactory {
public StoreWithFactory() {
// If the constructor is private or public doesn't matter
// unless you do TDD, in which you need to have a public
// constructor to create the object so you can test it.
}
// The method returning an instance of Singleton is now a
// factory method.
public static StoreWithFactory getInstance() {
return new StoreWithFactory();
}
}
// Usage:
// var myStore = StoreWithFactory.getInstance();
用法仍然相同,但您不会因拥有单个实例而陷入困境。自然地,您会将这个工厂方法移到它自己的类中,因为Store
该类不应该关心自己的创建(并且巧合地遵循单一责任原则作为将工厂方法移出的效果)。
从这里你有很多选择,但我会把它留给你自己练习。这里很容易对模式进行过度设计(或过热)。我的建议是仅在需要时应用模式。