Eliminar todas las claves de un diccionario NSUserDefaults iOS

Utilizo el diccionario NSUserDefaults para almacenar información básica, como puntuaciones altas, etc., de modo que cuando el usuario cierra la aplicación, los datos no se pierden. De todos modos yo uso:

NSUserDefaults *prefs = [NSUserDefaults standardUserDefaults]; 

para almacenar datos. Si deseo almacenar un nuevo puntaje alto, por ejemplo, lo haría:

 [prefs setInteger:1023 forKey:@"highScore"]; [prefs synchronize]; //this is needed in case the app is closed. 

y más tarde si deseo recuperar la puntuación más alta que haría:

 [prefs integerForKey:@"highScore"]; 

de todos modos, el punto es que NSUserDefaults enable muchas otras cosas porque NSUserDefaults enable te permite almacenar booleans , integers , objects , etc. ¿Qué método debo ejecutar para eliminar todas las claves de modo que NSUserDefaults sea como la primera vez que ejecuto la aplicación?

Estoy buscando algo como:

 NSUserDefaults *prefs = [NSUserDefaults standardUserDefaults]; [prefs deleteAllKeysAndObjectsInTheDictionary]; 

o tal vez hay una forma de obtener todas las claves y tengo que recorrer cada objeto, pero no sé cómo eliminarlas.

EDITAR:

Yo he tratado :

 NSUserDefaults *prefs = [NSUserDefaults standardUserDefaults]; [NSUserDefaults resetStandardUserDefaults]; [prefs synchronize]; 

y aún puedo recuperar un puntaje alto …

Si echas un vistazo a la documentación de NSUserDefaults , verás un método - (NSDictionary *) dictionaryRepresentation . Usando este método en los valores predeterminados del usuario estándar, puede obtener una lista de todas las claves en los valores predeterminados del usuario. A continuación, puede usar esto para borrar los valores predeterminados del usuario:

 - (void)resetDefaults { NSUserDefaults * defs = [NSUserDefaults standardUserDefaults]; NSDictionary * dict = [defs dictionaryRepresentation]; for (id key in dict) { [defs removeObjectForKey:key]; } [defs synchronize]; } 

La forma más sencilla de hacer esto con los mismos resultados, como en la respuesta principal de Alex Nichol:

 NSString *appDomain = [[NSBundle mainBundle] bundleIdentifier]; [[NSUserDefaults standardUserDefaults] removePersistentDomainForName:appDomain]; [[NSUserDefaults standardUserDefaults] synchronize]; 

Un trazador de líneas

 [[NSUserDefaults standardUserDefaults] removePersistentDomainForName:[[NSBundle mainBundle] bundleIdentifier]]; 

Solución simple

C objective:

 NSString *appDomain = [[NSBundle mainBundle] bundleIdentifier]; [[NSUserDefaults standardUserDefaults] removePersistentDomainForName:appDomain]; 

En Swift 3.0:

 if let appDomain = Bundle.main.bundleIdentifier { UserDefaults.standard.removePersistentDomain(forName: appDomain) } 

Versión Swift:

 if let bid = NSBundle.mainBundle().bundleIdentifier { NSUserDefaults.standardUserDefaults().removePersistentDomainForName(bid) } 

+ (void) resetStandardUserDefaults no conserva los cambios, simplemente restablece el objeto predeterminado de usuario en memoria para que la próxima llamada de synchronize se lea desde la copia en disco, en lugar de sobreescribir valores existentes en memoria con el disco versiones.

La iteración sobre las claves es mejor, pero en realidad hay una función que hace esto por usted: removePersistentDomainForName:

 // you can usually get the domain via [[NSBundle mainBundle] bundleIdentifier] [[NSUserDefaults standardUserDefaults] removePersistentDomainForName:[[NSBundle mainBundle] bundleIdentifier]]; // or use a string for any other settings domains you use //[[NSUserDefaults standardUserDefaults] // removePersistentDomainForName:@"com.mycompany.myappname"]; [[NSUserDefaults standardUserDefaults] synchronize]; 

Al final de la operación de synchronize , tanto el disco como las copias de memoria de los valores predeterminados del usuario no contendrán ninguno de los valores establecidos por su aplicación.

Para aquellos de ustedes que quieran hacer esto en el objective de la prueba, removePersistentDomain (ya que removePersistentDomain no funciona para ese caso)

Swift 3:

 for key in Array(UserDefaults.standard.dictionaryRepresentation().keys) { UserDefaults.standard.removeObject(forKey: key) } 

Oneliner en Swift:

Swift 3

 NSUserDefaults.standardUserDefaults().removePersistentDomainForName( NSBundle.mainBundle().bundleIdentifier!) 

Swift 4

 UserDefaults.standard.removePersistentDomain(forName: Bundle.main.bundleIdentifier!) 

Para Swift 3:

 let appDomain = Bundle.main.bundleIdentifier! UserDefaults.standard.removePersistentDomain(forName: appDomain) 

Para Swift 3:

 if let bundle = Bundle.main.bundleIdentifier { UserDefaults.standard.removePersistentDomain(forName: bundle) } 

Rápido

  func resetUserDefaults(){ let userDefaults = NSUserDefaults.standardUserDefaults() let dict = userDefaults.dictionaryRepresentation() as NSDictionary for key in dict.allKeys { userDefaults.removeObjectForKey(key as! String) } userDefaults.synchronize() } 

¿Este método no hace eso?

 + (void)resetStandardUserDefaults 

De la documentación para NSUserDefaults :

resetStandardUserDefaults

Sincroniza cualquier cambio realizado en el objeto predeterminado de usuario compartido y lo libera de la memoria.

+ (void)resetStandardUserDefaults

Discusión

Una invocación posterior de standardUserDefaults crea un nuevo objeto predeterminado de usuario compartido con la lista de búsqueda estándar.

En base a esto, puedes hacer:

 [NSUserDefaults resetStandardUserDefaults]; [NSUserDefaults standardUserDefaults]; 

y ahora los valores predeterminados deben restablecerse.

Swift 3 o 4 Incluso podemos simplificar el fragmento descrito en esta expresión moderna:

 func clearAll() { let settingsDictionary = userDefaults.dictionaryRepresentation() settingsDictionary.forEach { key, _ in userDefaults.removeObject(forKey: key) } userDefaults.synchronize() } 

Rápido
colocar en tu lógica

 if let appDomain = Bundle.main.bundleIdentifier { UserDefaults.standard.removePersistentDomain(forName: appDomain) }