什么时候在对象中使用工厂方法而不是factory类是一个好主意?
当前回答
当它们返回的对象类型具有私有构造函数时,当不同的工厂类在返回的对象上设置不同的属性时,或者当特定的工厂类型与其返回的具体类型耦合时,工厂类非常有用。
WCF使用ServiceHostFactory类来检索不同情况下的ServiceHost对象。IIS使用标准的ServiceHostFactory来检索.svc文件的ServiceHost实例,但是WebScriptServiceHostFactory用于向JavaScript客户端返回序列化的服务。ADO。NET Data Services有自己特殊的DataServiceHostFactory和ASP。NET有它的ApplicationServicesHostFactory,因为它的服务有私有构造函数。
如果只有一个类在使用工厂,那么可以在该类中使用工厂方法。
其他回答
清楚地区分使用工厂或工厂方法背后的思想是很重要的。 两者都旨在解决互斥的不同类型的对象创建问题。
让我们具体谈谈“工厂方法”:
首先,当您正在开发库或api时,这些库或api将用于进一步的应用程序开发,那么工厂方法是创建模式的最佳选择之一。原因;我们知道什么时候创建一个所需功能的对象,但对象的类型仍未确定,或者将根据传递的动态参数来决定。
Now the point is, approximately same can be achieved by using factory pattern itself but one huge drawback will introduce into the system if factory pattern will be used for above highlighted problem, it is that your logic of crating different objects(sub classes objects) will be specific to some business condition so in future when you need to extend your library's functionality for other platforms(In more technically, you need to add more sub classes of basic interface or abstract class so factory will return those objects also in addition to existing one based on some dynamic parameters) then every time you need to change(extend) the logic of factory class which will be costly operation and not good from design perspective. On the other side, if "factory method" pattern will be used to perform the same thing then you just need to create additional functionality(sub classes) and get it registered dynamically by injection which doesn't require changes in your base code.
interface Deliverable
{
/*********/
}
abstract class DefaultProducer
{
public void taskToBeDone()
{
Deliverable deliverable = factoryMethodPattern();
}
protected abstract Deliverable factoryMethodPattern();
}
class SpecificDeliverable implements Deliverable
{
/***SPECIFIC TASK CAN BE WRITTEN HERE***/
}
class SpecificProducer extends DefaultProducer
{
protected Deliverable factoryMethodPattern()
{
return new SpecificDeliverable();
}
}
public class MasterApplicationProgram
{
public static void main(String arg[])
{
DefaultProducer defaultProducer = new SpecificProducer();
defaultProducer.taskToBeDone();
}
}
工厂方法应该被认为是构造函数的替代品——尤其是在构造函数表达能力不够的时候。
class Foo{
public Foo(bool withBar);
}
表现力不如:
class Foo{
public static Foo withBar();
public static Foo withoutBar();
}
当你需要一个复杂的过程来构造对象时,当构造需要一个你不想要的实际类的依赖关系时,当你需要构造不同的对象时,工厂类是有用的。
这真的是个品味问题。工厂类可以根据需要进行抽象/接口,而工厂方法是轻量级的(而且往往是可测试的,因为它们没有定义的类型,但它们需要一个众所周知的注册点,类似于服务定位器,但用于定位工厂方法)。
我认为这取决于你想要给你的代码带来的松耦合程度。
工厂方法解耦得很好,但是工厂类不行。
换句话说,使用工厂方法比使用简单的工厂(称为工厂类)更容易更改内容。
看看这个例子:https://connected2know.com/programming/java-factory-pattern/。现在,想象一下你想要带来一个新的动物。在Factory类中,您需要更改Factory,但在Factory方法中,不需要,您只需要添加一个新的子类。
在对象中使用工厂方法是个好主意:
对象的类不知道它必须创建什么确切的子类 Object的类被设计成它创建的对象由子类指定 对象的类将其职责委托给辅助子类,并且不知道确切的类将承担这些职责
在以下情况下使用抽象工厂类是个好主意:
对象不应该依赖于其内部对象是如何创建和设计的 一组链接的对象应该一起使用,您需要满足这个约束 对象应该由几个可能的链接对象家族中的一个来配置,这些对象将成为父对象的一部分 它需要共享只显示接口而不显示实现的子对象