2

I have a login view controller in which the user enters their preferences like whether or not he wants to activate certain UI features.

I store these as variables whose getters and setters directly access UserDefaults, here is an example of one of these:

class Preferences {
        static var likesSpaghetti : Bool {
            set (likesSpaghetti) {
                UserDefaults.standard.set(likesSpaghetti, forKey: "likesSpaghetti")
            }

            get {
                return UserDefaults.standard.bool(forKey: "likesSpaghetti")
            }
        }
}

So that whenever I want to set any of these I simply write something like this:

Preferences.likesSpaghetti = false

Now, my question is: Can I set these variables every time the user flicks the on/off switch or should I keep the preference represented as a local variable and then only set:

Preferences.likesSpaghetti = spaghettiSwitch.isOn

when the user segue's away from the loginViewController? Is every access of UserDefault instant and quick? or is it laggy and should be used mercifully?

Edit after closing this question: So I learned to not prematurely optimize, and that it is probably ok within the scope of a few dozen elements. So I should be fine. I'm going to just update every time the user modifies anything so that my code is a lot easier to read and maintain.

Thanks everyone!

JoeVictor
  • 1,806
  • 1
  • 17
  • 38

3 Answers3

8

Your code is just fine. Don't worry about such optimizations until you actually encounter an issue. Trust that UserDefaults is implemented smartly (because it is). There is nothing "laggy" about setting something as simple as a Bool in UserDefaults.

You also wish to review another one of my answers which is related to this question: When and why should you use NSUserDefaults's synchronize() method?

rmaddy
  • 314,917
  • 42
  • 532
  • 579
  • Your linked answer was very helpful. One last followup, what if the data is somewhat larger? Like a set of enums representing preferences? I'm talking AT MOST 10 items in the set. I currently have 5. This is fairly light, right? Is there any way I can be sure? – JoeVictor Feb 12 '18 at 22:03
  • @QuantumHoneybees The best way is to try it, and change it only if it becomes a performance problem. As Knuth said, [premature optimization is the root of al evil](https://en.wikipedia.org/wiki/Program_optimization#When_to_optimize). – NobodyNada Feb 12 '18 at 22:12
  • 1
    @QuantumHoneybees I see no issue with a dozen values. The problems start when storing image data or large array/dictionaries of data. – rmaddy Feb 12 '18 at 22:14
2

Actually userDefaults (it's originally a plist file) is used for this purpose which is storing app settings and that light-wight content creating a variable may consum memory if you have to configure many of them , besides not reflecting the new setting change directly to defaults made by user , may cause un-expectable old settings to happen at the time of change such as a localized alert or part of code (such as push notification callback) that check the same setting where the user thinks it's already reflected

Shehata Gamal
  • 98,760
  • 8
  • 65
  • 87
1

Adding to both @rmaddy @Sh_Khan, if you think about the security aspect of it, NSUserDafault is exactly for the details which is app specific such as settings, preferences or some configurations which are not security sensitive while things like passwords, usernames and sensitive data are not recommended to store in UserDefaults. You should use services like keychain which is encrypted for such data.

Gihan
  • 2,476
  • 2
  • 27
  • 33