我理解工厂模式已实施但无法获得它带来的好处。例如,而不是:
MyType1 obj=new Mytype1();
MyType2 obj=new Mytype2();
写作:
IMyType obj1 = Factory.Create(1);
IMyType obj2 = Factory.Create(2);
这是我错过了还是没有想到的东西。你能不能把自己的经验付诸实践。
答案 0 :(得分:3)
工厂模式的一些好处:
答案 1 :(得分:1)
出于多种原因,工厂模式很好
其中几个是:
构造函数是创建项的一种方法,但是如果不将类紧密耦合到这些依赖项,则无法检查其他类或运行新创建的实例之外的其他进程
这些是我能想到的一些原因:)
e.g。
此类依赖于ConfigManager进行实例化
class SomeClass
{
public int SomeValue;
public SomeClass()
{
// Check the config for some value
SomeValue = ConfigManager.GetDefaultInt("SomeValue");
}
}
这个课不是因为它使用工厂
class SomeClass
{
public int SomeValue;
public SomeClass()
{
}
}
class SomeClassFactory
{
public SomeClass CreateSomeClass()
{
SomeClass obj = new SomeClass();
obj.SomeValue = ConfigManager.GetDefaultInt("SomeValue");
}
}
答案 2 :(得分:1)
Factory模式的好处在于它根据使用方式封装了构造细节和特定类型。这使您可以在以后用更少的地方进行更改,从而演变为更有趣的设计。
考虑这个例子:
public interface IStorage
{
void Save(SomeObject toSave);
SomeObject Get(SomeId id);
}
public class DatabaseStorage : IStorage
{
public void Save(SomeObject toSave)
{
//persist to DB somehow
}
public SomeObject Get(SomeId id)
{
//get from db somehow and return
}
}
public class StorageFactory
{
public IStorage GetStorage()
{
return new DatabaseStorage();
}
}
public class DatabaseStorage : IStorage
{
public void Save(SomeObject toSave)
{
//persist to DB somehow
}
public SomeObject Get(SomeId id)
{
//get from db somehow and return
}
}
现在假设您以后需要缓存一些结果,或者记录所有结果。您可以创建一个代理,如下所示:
public class LoggingStorage : IStorage
{
private readonly IStorage _proxied;
public LoggingStorage(IStorage proxied)
{
_proxied = proxied;
}
public void Save(SomeObject toSave)
{
//log this call
_proxied.Save(toSave);
}
public SomeObject Get(SomeId id)
{
//log this call
return _proxied.Get(id);
}
}
现在,如果您使用了构造函数,则必须替换它的每次使用以将其包装。如果您使用了工厂,则只需更改它:
public class StorageFactory
{
public IStorage GetStorage()
{
return new LoggingStorage(new DatabaseStorage());
}
}
当然,投机工厂看起来有点沉重,这就是为什么我更喜欢encapsulate the constructor。
答案 3 :(得分:1)
jQuery是一个工厂函数,它利用JavaScript的工作方式来创建内存占用非常少的对象。
让我们通过一个可怕的残缺,大幅简化的jQuery版本进行调查,以帮助我们了解潜在的好处:
var $ = jQuery = (function(){ //this anon function fires once, and returns a function
//defines all kinds of internal functions jquery uses here
function jQuery(selector,context){ // we're going to return this inner JQ later
//defines only the logic needed to decide what to do with the arguments here
//and then builds the jQuery object with 'return new jQuery.prototype.init();'
}
//defines jQuery.prototype properties here:
jQuery.prototype = {
//...
init:function(selector,context){ //gets used to build the JQ objects
this.constructor.prototype = jQuery.prototype; //hands off the function prototype
}
//...
}
return jQuery; //this gets assigned to the outer jQuery and $ vars
})()
所以...现在我们有一个工厂函数,它也像命名空间,我们可以扩展它的原型,并期望这些方法在它吐出的对象上可用。此外,除了它们通常包装的DOM对象之外,对象本身在内存中的权重非常小,因为所有函数都是从闭包中引入的引用或作为引用传递的外部原型对象。除了一些逻辑和一些状态变量之外,在向工厂函数的原型属性添加新方法时,当jQuery首次被解析或传递给原型对象时,构建对象所需的一切。
现在,尝试使用new jQuery()
如果有的话,在JavaScript中应用工厂模式可以是非常强大的。