When you need to store a dictionary, there are a few different options for doing so.
First, a quick note about
Info.plist. You don’t need to manually read in a file to access the contents of this file as a dictionary: you can just call
URLs to the docs directory
First, let’s talk about how to refer to file locations. The
URL is the main way locations are referred to, even though they’re local URLs on the device.
To write files, you use the documents directory. The base documents directory is a bit more complex to calculate, because it uses the same API as on macOS, where there are more options:
let docsBaseURL = FileManager.default.urls(for: .documentDirectory, in: .userDomainMask).first!
From there, you can get the path to a specific file by adding a path component again:
let customPlistURL = docsBaseURL.appendingPathComponent("custom.plist")
Reading and Writing Plists
To read a property list file, you can use a constructor built in to
let customDict = NSDictionary(contentsOf: customPlistURL) as? [String : AnyObject]
NSDictionary is the old Objective-C dictionary class; if you’re working in swift, you probably want a Swift-style dictionary, which is why it’s cast to
[String : AnyObject].
To write a property list, there is also a method built in to
NSDictionary(dictionary: customDict).write(to: customPlistURL, atomically: true)
We need to use a
NSDictionary constructor again to turn the Swift dictionary back into an
NSDictionary. If you used the
NSDictionary as-is, you wouldn’t need to translate it.
Note that the value type of the Swift array is
Any. this means that the values of the dictionary have to be objects, so
Doubles can’t be used. Instead, you need to wrap them in a
NSNumber. If you would rather be able to use
Doubles directly, there’s another option: archives.
Reading and Writing Archives
Archives can be used to store a wide variety of types, including Swift dictionaries. To read an archive, you use the
let customDict = NSKeyedUnarchiver.unarchiveObject(withFile: customArchiveURL.path) as? [String: Any]
unarchiveObject() takes a path String instead of a URL, but all you need to do differently is access the
path attribute of the
Note, as well, that the type of the object we unarchived is a Swift dictionary with a value of type
Doubles can be used directly.
To save an archive, you use
NSKeyedArchiver.archiveRootObject(dictionary, toFile: url.path)