0

I'm testing this code in playground. What I don't understand is, why is result always nil? Thanks for help

var value: String!
let key = "key24"

if value == nil{
    value = "hehe"
    let valueNS = NSString(string: value)


    NSUserDefaults.standardUserDefaults().setValue(valueNS, forKey: key)
}



var result: AnyObject? = NSUserDefaults.standardUserDefaults().objectForKey(key)
print(result)

enter image description here

potato
  • 4,479
  • 7
  • 42
  • 99

1 Answers1

2

There's something screwy going on with playgrounds, especially with Xcode 7. I can get a variation on your code to work on Xcode 6.4, with a few changes:

You should use setObject:forKey not setValue:forKey.

You should cal synchronize after changing defaults.

Here's the modified code (which works in Xcode 6.4, although testing it in Xcode then causes Xcode 6.4 to fail as well.)

//: Playground - noun: a place where people can play

import UIKit

var value: String!
let key = "key24"


if value == nil
{
  value = "hehe"
  print("value was nil!")
  NSUserDefaults.standardUserDefaults().setObject(value, forKey: key)
  NSUserDefaults.standardUserDefaults().synchronize()
}

var result = NSUserDefaults.standardUserDefaults().stringForKey(key)
print(result)
Duncan C
  • 128,072
  • 22
  • 173
  • 272
  • 1
    Calling `synchronize()` is both unnecessary and recommended against by Apple. It's never necessary to call in normal usage. Check the Foundation docs for the few instances in which it's actually necessary. – Jon Shier Sep 13 '15 at 21:38
  • 1
    And yet when I tested it the stringForKey call returned nil without it, and returned the value correctly when I added it. – Duncan C Sep 13 '15 at 22:10
  • I'm going to go with the "ground truth" of what works. – Duncan C Sep 13 '15 at 22:11
  • Calling `synchronize` is only needed if you kill the app or the app crashes before iOS synchronizes `NSUserDefaults` for you. – rmaddy Sep 13 '15 at 22:25
  • I understand that that is what Apple says, but in this case adding the call to synchronize makes the second call to stringForKey return the correct value, while without it, you get nil. – Duncan C Sep 13 '15 at 22:28
  • 1
    Which makes no sense, as that's not how `NSUserDefaults` works. Any value added is immediately accessible. Perhaps it's an issue with playgrounds. In a real app it's unnecessary. – Jon Shier Sep 13 '15 at 23:19
  • Probably so. Not sure how playgrounds interact with the app sandbox, bundles, etc. Not well, apparently. – Duncan C Sep 14 '15 at 13:44
  • I was getting nil every single time while retrieving from nsuserdefaults and synchronize did the trick...thank you – user578386 Jun 19 '16 at 07:54
  • @user578386, So this odd behavior in playgrounds still exists in Xcode 7.3? Sigh... – Duncan C Jun 19 '16 at 11:15