iOS 10 Core Data Tutorial - NSPersistentContainer - objective-c

I am attempting to follow Apples developer documentation to use CoreData.
I have just started learning Objective-C and now trying to wrap my head around CoreData. I think I have the concept under wraps OO Database.
For the life of me I can't get it to work and all searches I've done bring back either the tutorials for iOS 9 and previous, or for Swift.
Any help or guidance would be appreciated.
Core Data - Developer.Apple.Com

If you want to keep things simple only deal with a single managedObjectContext. If you are using NSPersistentContainer this is the viewContext. Make sure to always read and write to core-data only from the main thread. You will find similar simple setups with a single managedObjectContext in many tutorials.
Once you have mastered that you should learn how to use NSPersistentContainer properly. It is not that hard there are a few simple rules to follow:
NEVER write to the viewContext
only write using performBackgroundTask.
Do not use any managedObjects or context from performBackgroundTask
Do not use any viewContext managedObject inside of performBackgroundTask - pass the objectID and refetch it inside the context.
don't use newBackgroundContext - it is useful only in very rare situations that you are unlikely to encounter.
discard all managedObject after a fetch. If you need to keep a point to a managed object use a fetchedResultsController - even if it is for just one object

Related

Arguments for/against using Singleton Services + Notifications instead of nested controllers?

I have been endeavoring to wrap my head around building larger apps using the recommended MVC approach that most of the apple docs and various tutorials seem to embrace. That is, nested controllers each holding their own view, and while I 'get it', I don't necessarily like it -- in my particular app, I have a view (and controller) hierarchy that's now several classes deep. For example, a main controller/view -> sidebar -> upper half of sidebar (NSSplitView in an NSView) -> NSTableView.
I've been playing with passing the data/objects I need up and down this hierarchy, but it's getting kind of messy and seems to be leading me down a tight-coupling road I don't like very much, passing lots of things in the init methods for each controller -- for instance a data model.
I've also played with an idea a friend suggested, a singleton service. Essentially, it's a wrapper around whatever data model or 'thing' my controllers might need, in my case an EKEventStore that surfaces an NSArray property and emits notifications (on the main thread). So far this approach seems to be leading me down the road of much cleaner code, and certainly makes unit testing easier (I think), but I'm wondering if I'm way off with my approach.
Has anyone taken this approach before with large apps? Are there any pitfalls or land mines I'm about to stumble on? I realize a lot of this is style/preference, but I'm curious if I'm headed down a bad path.
Is your singleton just holding collections of objects to use or is it also holding mutable global state? For object instantiation and easy testing you should take a look at a DI implementation like Objection. For test mocking check out OCMock.
Using Objection, you can inject a DataModelService into any controller that needs access to the data model for example.

Objective-c class design/organization

I've created my first iPhone app that presents audio tracks of a similar genre in a tableview. The user can play audio tracks using ipod-like controls which streams mp3.
All of my code is in two main classes: RootViewController and CustomCell.
My RootViewControllerClass is massive. I'm assuming it is poor design to stuff almost all of my code in one class?
Initially, I thought it made sense because I only have one View Controller. To practice better coding conventions, I'd like to split up my RootViewController class into smaller, specific classes (assuming this is the correct practice?).
Here are the components of RootViewController that I plan to separate out into individual classes:
DataSource - pulls data from server; modifies and organizes the data for the tableView
TopChartsView - includes buttons in a view to modify the audio tracks(dataSource) by top rated weekly/monthly/all-time
GenreChange - includes buttons in a view to filter the dataSource by genre
AudioPlayerControls - includes buttons in a view that are similar to iPod controls
Am I organizing my classes correctly? It seems to make sense that I organize my classes by function. However, I'm having difficulty grasping how classes should interact with each other in an ideal design.
Do I use protocols and delegation to link my classes together?
Designing iOS apps is mostly about the MVC design pattern, which means that you seperate your model, view and controller. In your case I would put the DataSource logic in a seperate file or files (it's your model). This also makes it easier to reuse the same logic in another view controller in a later point. Maybe you can also subclass your UITableView if lots of code resides there.
Protocols and delegates are a great way to connect your classes and they are very frequently used in a good design. Since you don't have many viewcontrollers in your application (as far as I see), there are not very much opportunities to use them, please correct me if I'm wrong ;)
It's more about object-oriented-programming than especially about iOS and I think, you should get familiar with some concepts of OO-Design (if you really interested), but from my point of view you don't have to. To answer your questions first:
I'm assuming it is poor design to stuff almost all of my code in one class?
Some say so...
Am I organizing my classes correctly?
Hard to tell, by the information you gave.
Do I use protocols and delegation to link my classes together?
Not necessarily.
But: If your code works fine, you are the only one, who works on it, you don't plan to re-use your code as a library or by taking full classes from it (i.e. if you only plan to copy & paste), there is no need to refactoring everything just for the sake of doing it.
Even though: If you want to move forward or if you're planning to write libraries or something, it would be a good idea to learn about OO (sometimes it's even entertaining). Since you're working with objective-c this one from apple's docs could be a good start to learn.
And: If you read a bit about OO-programming and (more important) take the time and to read code of others, you'll know how and when it is useful to organize your own code.

Do I need to use a delegate to maintain the MVC pattern when accessing NSUserDefaults?

Still on assignment 4 of cs193p. - http://www.stanford.edu/class/cs193p/cgi-bin/drupal/system/files/assignments/Assignment%204_2.pdf
I've fully (ish) implemented the displaying photos from a list of places.
I'm adding the second tab of the application (required tasks 10 & 11) , which is to generate and display a list of the 20 most recent photos viewed in chronological order.
My question relates to the MVC pattern and setting/accesing NSUserdefaults.
Basically, anytime a photo is viewed, a property list stored in NSUserdefaults needs to be updated.
When selecting the "recent photos" tab, those values need to be read and displayed, so that the user can select a recently viewed photo, and then view it by selecting it.
I think I can implement this quite easily from a writing lines of code and it will probably work point of view.
I've seen this question: CS193P UITabBarController MVC Help on Assignment 4 which is kind of related, but doesn't really address my more theoretical question about the nature of the pattern.
My question is more about the MVC pattern.
In the lecture, when he demonstrated this with favourite graphs, from the previous calculator assignment he used a delegate to communicate between the favourites list view controller and the graphviewController (see diagram on slide 64 of lecture 9). http://www.stanford.edu/class/cs193p/cgi-bin/drupal/system/files/lectures/Lecture%209_1.pdf
I'm trying to work out if I need to do something similar to avoid breaking the MVC pattern, or if I can just use NSUserdefaults in both the viewWillLoad of my imageViewController to add a photo to the favourites and and then in my setter in RecentImagesViewController. I know NSUserdefaults is designed for persistence, it just feels a bit like I"m using a global variable.
I realise this question is worded in a way which makes it difficult to follow if you aren't familiar with the cs193p course - sorry.
Thanks for any advice!!
I don't think you have to transform something rather simple in something complex. You are storing the favorites using the NSUserDefaults and that's it. The place where you are using might not be the best (I am not saying the viewWillLoad is a bad place, I don't know your code), but I don't think you need a delegate to just update the NSUserDefaults. Botton line, don't forget the KISS principle. :)
Well, it probably feels like you're using a global variable because the user defaults themselves are a global concept. And they should be. You don't want different parts of the app operating on unsynchronized versions of user preferences.
But, if you use the term variable in the sense of an old C/C++ global static piece of data, then, no ... that's not what it is. NSUserDefaults was written by Apple to be a nice tidy class that encapsulates the user default data. The fact that you use [NSUserDefaults standardUserDefaults] to access something like a singleton instance (not sure if that's how Apple chose to implement it) still doesn't mean it's a true global variable.
I agree with Jacky Boy that keeping it simple is best, but your question is really asking whether doing it the way you are is a violation of the MVC pattern (and adhering slavishly to a pattern is not always going to make your code the best). That depends on what you consider the model to be. I could justify saying that Apple built NSUserDefaults to be a model layer encapsulation of the preferences data. So, there you have your model layer, and your controllers should be able to use it.
Or do you feel the need to write the entire model layer yourself, in which case your model layer would just have a wrapper for NSUserDefaults. That would seem like overkill for most situations.
Here is maybe one situation that could warrant it. If you have a lot of preference data that seems logically related, but some of it is not appropriate for NSUserDefaults. Perhaps it's a lot of binary data, stored in a hierarchy of objects, and you want to persist it with Core Data. But, it still seems logically related to what you're keeping in NSUserDefaults. Maybe then, you decide to write your own model layer, that encapsulates both the Core Data and NSUserDefaults data. Your view controllers could then use that directly.
But, generally, I think iOS is well designed to have whoever needs to just use the standardUserDefaults object directly.
If I understand the question correctly, it sounds like the setting/loading should be occurring from the appropriate view controller. Creating a delegate (which may or may not be a singleton) that you can call from each of the different tab's view controllers will help prevent you from duplicating code.

Multiple ViewControllers - should I use a singleton object?

I have a new project, kind of a board game, and I'm using a storyboard which has multiple view controllers in it - the game simply moves from one view to the next with the player making various decisions and then loops back.
I have an object which holds information about the player (along with a couple of methods) - the score etc. I obviously only need one instance of this object and as I want each View Controller to access the same instance, should it be a singleton? I've never used them before and I've read they're often over-used, so I just want to check if this is the correct way to do this from the start. Many thanks.
What you have described is the Model for your application, holding the game data and core logic. Is there any reason to make this a singleton rather than passing it between your controllers?!
I would assume one controller calls the next and so can pass this information across?! We use singletons for services and the like but not for model data, it's not really the point of them in our experience.
I personally have nothing against singletons, as long as you don't use too many of them in one project. While other people might recommend you use some other mediation for this project, I say go for it—this is exactly what you'd use a singleton for.
Singleton's can be be bad if you are developing a library component, a large server project, or for unit testing. But since you are doing an iphone game don't fret about it, it'll will be easier and faster just to use a singleton.
If you are worried about unit testing, since objetive-c is latebound and singletons are made with factory methods instead of constructors it's not hard to changeout the singleton for your unit test anyway.

Mapping obj-c object to sqlite database

Im looking for a simple (if I can call it that) mapping tool for obj-c, that maps objects and their relationships to a sqlite database. Is there any out there that acts like db4o for java? I havent found anything on google, and I think its because Im not completly sure of where to look and what to look for.
Hope someone can help, because I dont want to write my own mapping tool to sqlite.
EDIT
it seems like entropyDb does the job. http://code.google.com/p/entropydb/. But Im not sure yet.
I dont quite understand this line: "One cannot store instances of Cocoa classes directly. Collections (NSArray, NSSet, NSDictionary) can be stored if they are instance variables of custom objects." I read it like I cant store arrays and sets if they are instance variables of a custom object.
You're looking for Core Data, which is part of the iPhone SDK.