1

什麼是在Objective-C中獲取對「單例」對象的引用的好方法?請注意,具體而言,我不是指單例模式,我指的是通常只有一個實例的對象。這特別適用於應用程序模型。例如,在一個烹飪應用程序中,我想要一個類(RecipeModel),它可以爲我提供我係統中所有「食譜」對象的NSArray。在Objective-C(iPhone)中傳遞引用的靈活方式?

我不希望每次都從持久性存儲裝載這些數據 - 將它們加載一次,然後將它們緩存在內存中(換句話說,在這個類的變量中)是有意義的。如果我這樣做,我的幾個類可能需要一種方法來到這個實例。

什麼是最靈活的方式來做到這一點?以下是我能想到的所有選項。

  1. 讓RecipeModel一個真正的辛格爾頓,用+(RecipeModel *)sharedRecipeModel方法
  2. 製作的美食傑的NSArray通過類方法訪問。然後,每個viewController可以創建一個新的RecipeModel並獲得相同的(靜態/全局)數據。 +(NSArray的*)美食傑
  3. 中的appDelegate創建它,並使用sharedApplication得到一個參考吧
  4. 確保一切都在界面生成器,並使用一個IBOutlet到類的副本傳遞給我的viewController

在其他平臺(flex)上,我會使用DependencyInjection或MVC框架來處理這種佈線。我讀過Objective-C並不需要「DI框架」,因爲它具有類別。我不知道評估這個問題,但類別當然不能解決這個問題。

+0

有趣的閱讀:http://cocoawithlove.com/2008/11/singletons-appdelegates-and-top-level.html – fphilipe 2010-01-16 15:38:53

回答

1

我認爲你已經完成了這個複雜化。

當你需要的只是一個通用的集合對象時,沒有理由創建一個單例類,所有其他對象都可以訪問它。

對一些對象進行通用訪問的最佳方式是將其停放在應用程序委託中。在這種情況下,你認爲你會是這樣的:在您的應用程序

@interface mytAppDelegate : NSObject <UIApplicationDelegate> { 
    NSMutableArray *recipies; 
... 

然後在任何地方,你可以撥打:

UIApplicationDelegate *appDelegate=[[UIApplication sharedApplication] delegate]; 
RecipeObj *aRecipe=[appDelegate.recipes objectAtIndex:someIndexValue]; 

無事,沒有搞亂。

如果您使用核心數據,您可以將NSManagedObjectContext對象停放在應用程序委託中,並直接訪問該對象。核心數據具有巨大的優化,使其與更原始的手動滾動方法一樣快。除非您測試並發現直接核心數據的速度要慢,否則我不打算嘗試創建單獨的數組。在你提供的情況下,它不會。

+0

對於小型項目來說,這是一個很好的方法,但它不會縮放,因爲在那裏的大型項目在您的應用程序委託中將會太多垃圾,同樣,我想要一種封裝數據邏輯的方法。所以,你所建議的就是我所傾向的東西,而不是擁有這個數組,它會引用一個加載並提供該數組的類。 – 2010-01-16 23:59:59

+0

是的,你可以重載應用程序委託。首選方法是創建一個類來管理您的數據模型,然後將其作爲iVar駐留在應用程序委託中。這使得數據模型在項目之間非常便攜。我自己使用這種方法。如果您有複合模型例如一些數據存儲在覈心數據中,一些存儲在文件中。 – TechZen 2010-01-17 14:25:48

2

爲1,有一個像RecipeProvider類與allRecipes類方法返回一個包含所有食譜的數組。在該方法中,您可以執行加載/緩存/更新處理。要跟蹤數據和狀態,請在RecipeProvider類(非線程安全)中或直接在allRecipes函數中使用靜態變量。

1

我不確定是否有一個正確方式做到這一點,當然所有的選擇都是可行的。我個人的偏好是爲我的數據存儲創建一個單例對象,並添加方法來訪問「重要的東西」。在這種情況下,食譜的列表。

1

我使用應用程序委託來存儲對UIFontUIColor實例的引用,爲用戶界面創建事實上的「樣式」。其他控制器通過代理訪問這些實例。這對他們來說是一個很好的地方,因爲應用程序委託本質上已經是單例,這對於特定於應用程序的實體來說是一個明智的地方。

如果您認爲從應用程序委託中分離出來,您也可以創建一個RecipeModel正確的單身人士。這將實現相同的目標。