Persisting a datasource between multiple views without shared root view controller
I'm currently working on an app that uses a UINavigationController inside UITabBars. The tab bars correspond to both UITableViews as well as a Map View. However, the root view controller of the app is not the parent, or direct parent, of the UITableView custom controllers and map view controller. I also have a p-list that creates NSDictionary objects; it is the datasource that I am using to populate entries in the tables and the map.
So, without a root view controller, how should I create the NSDictionary objects from the data source? It seems to me that the easiest way is to simply recreate the object in each view controller for a view that needs the data. Because I don't have that many views and the p-list isn't that long, memory shouldn't be an issue. However, I do know that this is all very inefficient.
Is there any alternative implementation so that I don't have to recreate the NSDictionary in each view controller?
This tutorial featuring the singleton guide neatly explains everything: http://www.cocoanetics.com/2009/05/the-death-of-global-variables/
My only worry now is if multiple view controllers each call the singleton, wouldn't they all be generating multiple instances of the NSDictionary, and couldn't that conceivably still take up a lot of memory?
In practical terms, a data model is usually either placed in some kind of a singleton (either your own, or the app delegate which is a kind of singleton).
You need a data model object that stores the data for application.
A data model is a customized, standalone object accessible from anywhere in the application. The data model object knows nothing about any views or view controllers. It just stores data and the logical relationships between that data.
When different parts of the app need to write or read data, they right and read to the data model. In your case, view1 would save its data to the data model when it unloads and then view2 would read that data from the data model when it loads (or vice versa.)
In a properly designed app, no two view controllers should have access to the internal data of another controller. (The only reason a view controllers needs to know of the existence of another controller is if it has to trigger the loading of that other controller.)
The quick and dirty way to create a data model is to add attributes to the app delegate and then call the app delegate from the view controllers using:
MyAppDelegateClass *appDelegate=[[UIApplication sharedApplicaton] delegate]; myLocalProperty=appDelegate.someDataModelProperty;
This will work for small project but as your data grows complex, you should create a dedicated class for your data model.
Placing the data in an init method or a viewDidLoad won't work because in a tabbar the users can switch back and forth without unloading the view or reinitializing the view controller.
The best place to retrieve changing data is in the viewWillAppear controller method. That way the data will be updated every time the user switches to that tab.
You should read up on Model-View-Controller (MVC) architecture. Specifically, you'll probably want to introduce a data model where you would create and populate the dictionary during initialization and then access it from all of your view controllers.