2013-05-10 59 views
-1

首先,這完全是C#的問題!請將您的知識限制在C#中。工廠方法實現的含義

在我正在開發的應用程序中,我們有一些類可以提供預設的「原型」。處於非常高的水平:

public class Foo 
{ 
    #region Variables/Properties 

    public bool Bar { get; set; } 
    public string Name { get; set; } 
    public int Fooby { get; set; } 

    #endregion Variables/Properties 

    #region Prototypes 

    public Foo SomePrototype = new Foo 
    { 
     Bar = false, 
     Name = "Generic False State", 
     Fooby = -1 
    }; 

    public Foo SomeOtherPrototype = new Foo 
    { 
     Bar = true, 
     Name = "Generic True State", 
     Fooby = Int32.MaxValue 
    }; 

    #endregion Prototypes 

    #region Methods 

    // ...Behaviors here. 

    #endregion Methods 
} 

請注意「原型」部分。我一直了解,在C#中,「正確」的方式做這樣的「原型」是:

public Foo SomePrototype 
{ 
    get 
    { 
     return new Foo 
     { 
      Bar = false, 
      Name = "Generic False State", 
      Fooby = -1 
     }; 
    } 
} 

雖然我想無論是「原型」的實施可以工作,問:有一些什麼的在我們的代碼庫中看到的方式(即第一個示例?)的含義

對我來說,明顯的含義是,'原型'的所有用法都只是引用該公用的Foo變量,這可以提供一些有趣的交互......我只是想知道是否還有更多需要注意的事情。

+2

'Foo f = new Foo(); f.SomePrototype = new Foo {Name =「Baz」};' – I4V 2013-05-10 13:27:04

+0

這應該是一個答案。我很困擾我的基於getter的思維模式,我甚至都沒有看到。 – 2013-05-10 13:28:32

回答

1

在你的例子也有一些不同之處(從技術上看見過,裏面什麼都沒有做原型,但與C#的所有內容):

  • 例1:使用公共可寫域創建一次實例。
  • 示例2:將公共只讀屬性與每次調用創建的實例一起使用。

那麼,有什麼區別?

  • Foo不是不可變的。所以程序可以在代碼中的多個位置修改原型。在示例1的情況下,這將修改由所有其他代碼使用的原型(foo.SomePrototype.Fooby = -1),這可能是不希望的。
  • 公共字段是可寫的,因此程序可以修改對原型(foo.SomePrototype = new Foo {...})的引用,這會影響使用該原型的其他代碼。突然之間,原型可能會被取代。

現在關於原型:

  • 如果你看看原型模式(http://en.wikipedia.org/wiki/Prototype_pattern),它只是說,原型應該被用來創建一個新的克隆。
  • 讀那篇文章,你可以看到客戶端負責創建一個克隆,而不是類本身。有一個原型意味着你有一個實例並創建它的許多副本。您的財產正在創建每個電話的新實例。
  • 實際上,您正在使用工廠方法模式。那麼......好的,這是一個屬性,但它每次調用它時仍會創建一個對象。
  • 在我看來,我會去一個屬性,每次調用返回相同的引用。該引用存儲在私有(不是公用)字段中。這種方式參考永遠不會改變。

例子:

public class Foo 
{ 
    #region Variables/Properties 

    public bool Bar { get; set; } 
    public string Name { get; set; } 
    public int Fooby { get; set; } 

    #endregion Variables/Properties 

    #region Prototypes 

    static private Foo _SomePrototype = new Foo 
    { 
     Bar = false, 
     Name = "Generic False State", 
     Fooby = -1 
    }; 

    static private Foo _SomeOtherPrototype = new Foo 
    { 
     Bar = true, 
     Name = "Generic True State", 
     Fooby = Int32.MaxValue 
    }; 

    static public Foo SomePrototype 
    { 
     get 
     { 
      return _SomePrototype; 
     } 
    } 

    static public Foo SomeOtherPrototype 
    { 
     get 
     { 
      return _SomeOtherPrototype; 
     } 
    } 
    #endregion 
} 

反彈的問題:你想用什麼模式?原型模式還是工廠模式?

+0

我想我們如何使用它 - 工廠方法模式 - 是有效的。所以,應該改變一些地區名稱。感謝您的全面回答! – 2013-05-10 13:46:40

1

其含義非常簡單:第一個實現將可能的「原型」轉換爲「單例」。正如您正確指出的那樣,使用這種原型的所有東西都必須使用相同的實例。這是不可取的,因爲實例是可變的。您所代表的通用虛假和真實狀態的兩個對象將是單身很好的候選人,但你應該讓他們一成不變的,或通過只讀接口呈現出來:

interface IFoo { 
    bool Bar { get; } 
    string Name { get; } 
    int Fooby { get; } 
} 
public class Foo : IFoo { 
    ... 
    public static readonly IFoo SomePrototype = new Foo 
    { 
     Bar = false, 
     Name = "Generic False State", 
     Fooby = -1 
    }; 

    public static readonly IFoo SomeOtherPrototype = new Foo 
    { 
     Bar = true, 
     Name = "Generic True State", 
     Fooby = Int32.MaxValue 
    }; 
    ... 
} 
2

代碼這兩件不是同一事物的不同的實現,但服務不同勢的效果影響不大:

  • #1給你的東西像一個「實例單身」 ......從Foo單個實例派生將參考等於所有Someprototype秒。偉大的保存記憶,如果你永遠不會改變它們。
  • #2爲您提供每個調用的獨立實例。太好了,如果你需要修改它們。